HTML Guides for aria-label
Learn how to identify and fix common HTML validation errors flagged by the W3C Validator — so your pages are standards-compliant and render correctly across every browser. Also check our Accessibility Guides.
The aria-label attribute defines an accessible name for an element, providing a text label that assistive technologies (like screen readers) can announce to users. It's especially useful when there's no visible text label on screen, such as for icon buttons or navigation landmarks. However, aria-label doesn't work on every HTML element — it only has an effect on elements that have roles which support name from author.
According to the ARIA specification, aria-label is designed to work with interactive elements (like <button>, <a> with href, <input>), landmark and structural roles (like <nav>, <section>, <form>), images (<img>), and elements with explicit widget or landmark roles. When applied to generic elements that have no role (or only the generic implicit role), such as <div> or <span>, the attribute is effectively ignored by assistive technologies. This means users of screen readers won't hear the label, defeating its purpose entirely.
This matters for several reasons:
- Accessibility: Developers may believe they've provided an accessible label when they haven't. Users relying on screen readers will miss the information entirely.
- Standards compliance: The ARIA in HTML specification explicitly prohibits
aria-labelon elements where it has no effect, and the W3C validator flags this as a warning. - Maintainability: Meaningless attributes add noise to the codebase and can mislead future developers about the element's purpose.
To fix this warning, either move the aria-label to an appropriate element, add an explicit role attribute that supports naming, use aria-label on a different wrapping element that supports it, or replace the approach with visible text or a visually-hidden CSS class.
Examples
Incorrect: aria-label on a <div> with no role
A plain <div> has the implicit generic role, which does not support naming. The aria-label will be ignored.
<divaria-label="User profile section">
<imgsrc="avatar.jpg"alt="User avatar">
<p>Jane Doe</p>
</div>
Correct: Use a landmark element or add an appropriate role
Wrapping the content in a <section> element gives it the region landmark role (when labeled), making aria-label valid and meaningful:
<sectionaria-label="User profile section">
<imgsrc="avatar.jpg"alt="User avatar">
<p>Jane Doe</p>
</section>
Alternatively, add an explicit role to the <div>:
<divrole="region"aria-label="User profile section">
<imgsrc="avatar.jpg"alt="User avatar">
<p>Jane Doe</p>
</div>
Incorrect: aria-label on a <span>
<spanaria-label="Warning">⚠️</span>
The <span> has the generic role and does not support aria-label.
Correct: Use an appropriate role or element
<spanrole="img"aria-label="Warning">⚠️</span>
Incorrect: aria-label on a <p> element
<paria-label="Important note">Please read the terms carefully.</p>
The <p> element has the paragraph role, which does not support naming via aria-label.
Correct: Use visible text or restructure
If you need to provide additional context, consider restructuring:
<sectionaria-label="Important note">
<p>Please read the terms carefully.</p>
</section>
Or simply ensure the visible text is sufficiently descriptive, removing the unnecessary aria-label:
<p><strong>Important note:</strong> Please read the terms carefully.</p>
Common elements where aria-label works correctly
<!-- Interactive elements -->
<buttonaria-label="Close dialog">✕</button>
<ahref="/home"aria-label="Go to homepage">🏠</a>
<inputtype="search"aria-label="Search the site">
<!-- Landmark elements -->
<navaria-label="Main navigation">
<ul>
<li><ahref="/">Home</a></li>
</ul>
</nav>
<formaria-label="Newsletter signup">
<inputtype="email"aria-label="Email address">
<button>Subscribe</button>
</form>
<!-- Images -->
<imgsrc="chart.png"aria-label="Sales data for Q4 2024">
Quick reference: elements that do not support aria-label
Without an explicit role, aria-label will be flagged on these common elements: <div>, <span>, <p>, <b>, <i>, <em>, <strong>, <small>, <code>, <pre>, <blockquote>, <ul>, <ol>, <li>, <dl>, <dt>, <dd>, <table>, <thead>, <tbody>, and <tfoot>, among others. If you need aria-label on one of these, consider whether a more semantic element or an explicit ARIA role is the right solution first.
An aria-label attribute on an <a> element is only valid when the link has an accessible role that supports naming — which means the <a> must have an href attribute or an explicit role that accepts a label.
When an <a> element lacks an href attribute, it has the implicit role of generic. The generic role is in the list of roles that do not support naming, so applying aria-label to it is invalid. This is because a generic element has no semantic meaning, and screen readers wouldn't know how to announce the label in a meaningful way.
The most common cause of this error is using <a> as a placeholder or JavaScript-only trigger without an href. An <a> with an href has the implicit role of link, which does support aria-label, so the error won't appear.
You have a few ways to fix this:
- Add an
hrefto make it a proper link (most common fix). - Add an explicit role that supports naming, such as
role="button", if the element acts as a button. - Use a
<button>instead if the element triggers an action rather than navigation. - Remove
aria-labelif it's not needed, and use visible text content instead.
HTML Examples
❌ Invalid: aria-label on an <a> without href
<aaria-label="Close menu"onclick="closeMenu()">✕</a>
The <a> has no href, so its implicit role is generic, which does not support naming.
✅ Fix option 1: Add an href
<ahref="/close"aria-label="Close menu">✕</a>
✅ Fix option 2: Use a <button> instead
<buttonaria-label="Close menu"onclick="closeMenu()">✕</button>
✅ Fix option 3: Add an explicit role that supports naming
<arole="button"tabindex="0"aria-label="Close menu"onclick="closeMenu()">✕</a>
Using a <button> (option 2) is generally the best choice for interactive elements that perform actions rather than navigate to a URL.
A div element without an explicit role resolves to the generic role, which does not support naming — so adding aria-label to a plain div is invalid.
The aria-label attribute provides an accessible name for an element, but not every element is allowed to have one. The ARIA specification defines certain roles as "naming prohibited," meaning assistive technologies will ignore any accessible name applied to them. The generic role is one of these, and since a div without an explicit role attribute defaults to generic, the aria-label is effectively meaningless.
To fix this, you have two main options: assign an appropriate ARIA role to the div so it becomes a nameable landmark or widget, or switch to a semantic HTML element that already carries a valid role. Common roles that support naming include region, group, navigation, alert, and many others.
If the div is truly just a generic wrapper with no semantic meaning, consider whether aria-label is even needed. Perhaps the label belongs on a child element instead, or the content is already self-describing.
HTML Examples
❌ Invalid: aria-label on a plain div
<divaria-label="User profile section">
<p>Welcome, Jane!</p>
</div>
✅ Fix: Add an appropriate role
<divrole="region"aria-label="User profile section">
<p>Welcome, Jane!</p>
</div>
✅ Fix: Use a semantic element instead
<sectionaria-label="User profile section">
<p>Welcome, Jane!</p>
</section>
The aria-label attribute cannot be used on an <i> element with its default implicit role (generic), because generic elements are not allowed to have accessible names.
The <i> element has an implicit ARIA role of generic, which is one of the roles explicitly prohibited from carrying an aria-label. This restriction exists because screen readers and other assistive technologies ignore accessible names on generic containers — so adding aria-label to a plain <i> element would silently fail to convey any meaning to users who rely on assistive technology.
This issue commonly appears when icon fonts (like Font Awesome) use <i> elements as decorative icons. If the icon is purely decorative, you should hide it from assistive technology with aria-hidden="true" and place the accessible label on a parent or sibling element instead. If the icon conveys meaning on its own, you can assign an appropriate role like role="img" so the aria-label is actually announced.
HTML Examples
❌ Invalid: aria-label on a plain <i> element
<button>
<iclass="icon-search"aria-label="Search"></i>
</button>
✅ Fix 1: Decorative icon — hide it, label the parent
<buttonaria-label="Search">
<iclass="icon-search"aria-hidden="true"></i>
</button>
✅ Fix 2: Meaningful icon — assign role="img"
<button>
<iclass="icon-search"role="img"aria-label="Search"></i>
</button>
The aria-label attribute cannot be used on a custom element like <menu-item> when it has no explicit role attribute, because it defaults to the generic role, which is in the list of roles that prohibit aria-label.
Custom elements without an explicit role are treated as having the generic role (equivalent to a <span> or <div> in terms of semantics). The WAI-ARIA specification prohibits aria-label on several roles, including generic, because naming these elements creates a confusing experience for assistive technology users — a generic container with a label doesn't convey any meaningful purpose.
To fix this, you need to assign a meaningful role to the <menu-item> element that supports accessible naming. Common choices include role="menuitem", role="link", or role="button", depending on what the element actually does. Since this appears to represent a menu item that navigates to a page, role="menuitem" is likely the most appropriate.
HTML Examples
❌ Invalid: aria-label on an element with implicit generic role
<menu-item
submenu-href="/page"
label="some label"
submenu-title="some submenu title"
aria-label="some aria label">
</menu-item>
✅ Valid: adding an explicit role that supports aria-label
<menu-item
role="menuitem"
submenu-href="/page"
label="some label"
submenu-title="some submenu title"
aria-label="some aria label">
</menu-item>
If the aria-label isn't actually needed (for example, if assistive technology already receives the label through other means in your component), another valid fix is to simply remove aria-label entirely.
A span element has an implicit ARIA role of generic, and the aria-label attribute is not allowed on elements with that role.
The span element is a generic inline container with no semantic meaning. Its default ARIA role is generic, which is one of several roles that prohibit naming via aria-label or aria-labelledby. This restriction exists because screen readers are not expected to announce names for generic containers — adding aria-label to them creates an inconsistent and confusing experience for assistive technology users.
To fix this, you have two main options:
- Assign an explicit role to the
spanthat supports naming, such asrole="img",role="group",role="status", or any other role that allowsaria-label. - Use a different element that already has a semantic role supporting
aria-label, such as abutton,a,section, ornav.
If the span is purely decorative or used for styling, consider using aria-hidden="true" instead and placing accessible text elsewhere.
HTML Examples
❌ Invalid: aria-label on a plain span
<spanaria-label="Close">✕</span>
✅ Fixed: assign an appropriate role
<spanrole="img"aria-label="Close">✕</span>
✅ Fixed: use a semantic element instead
<buttonaria-label="Close">✕</button>
✅ Fixed: hide the decorative span and provide text another way
<button>
<spanaria-hidden="true">✕</span>
<spanclass="visually-hidden">Close</span>
</button>
The <time> element does not support the aria-label attribute when it has no explicit role or when it carries certain generic roles.
The <time> element has an implicit ARIA role of time, but this role is not listed among those that allow aria-label. According to the ARIA in HTML specification, aria-label is only permitted on elements with roles that support naming from author — and the default role of <time> (as well as roles like generic, presentation, paragraph, and others listed in the error) does not qualify.
In practice, the <time> element already conveys its meaning through its visible text content and the machine-readable datetime attribute. Screen readers use the visible text to announce the date, so aria-label is typically unnecessary.
To fix this, simply remove the aria-label attribute and ensure the visible text content is descriptive enough. If you need to provide a more accessible reading of the date, you can adjust the visible text itself or wrap the element with a <span> that has an appropriate role.
Also note the original code has a missing space before datetime — the attribute must be separated from class="Tag" by a space.
HTML Examples
❌ Invalid: aria-label on <time>
<timearia-label="Apr 2."class="Tag"datetime="2026-04-02">
Apr 2.
</time>
✅ Fixed: Remove aria-label and use clear visible text
<timeclass="Tag"datetime="2026-04-02">
April 2, 2026
</time>
If you truly need aria-label, you can assign an explicit role that supports naming, such as role="text", though this is rarely necessary:
<timerole="text"aria-label="April 2nd, 2026"class="Tag"datetime="2026-04-02">
Apr 2.
</time>
The aria-label attribute is not allowed on a label element that is associated with a form control through the for attribute.
A <label> element already provides an accessible name for the form control it's associated with. Adding aria-label to the <label> itself creates a conflict: the aria-label would attempt to override the label's own accessible name, but the label's visible text is what gets passed to the associated form control. This redundancy is not only unnecessary but explicitly prohibited by the HTML specification.
The <label> element's purpose is to be the accessible label for another element. If you want the form control to have an accessible name, simply put that text inside the <label> element as visible content. If you need to provide a different accessible name directly to the form control, place the aria-label on the input element instead.
Incorrect Example
<labelfor="input_email"id="label_input_email"aria-label="Email">
</label>
<inputtype="email"id="input_email">
Correct Example
The simplest fix is to remove the aria-label from the <label>, since the label's text content already serves as the accessible name for the input:
<labelfor="input_email"id="label_input_email">
</label>
<inputtype="email"id="input_email">
If you need the accessible name to differ from the visible label text, place aria-label on the input instead:
<labelfor="input_email"id="label_input_email">
</label>
<inputtype="email"id="input_email"aria-label="Your email address">
Validate at scale.
Ship accessible websites, faster.
Automated HTML & accessibility validation for large sites. Check thousands of pages against WCAG guidelines and W3C standards in minutes, not days.
Pro Trial
Full Pro access. Cancel anytime.
Start Pro Trial →Join teams across 40+ countries