About This HTML Issue
A <ul> element can't have role="tab": put role="tablist" on the list and role="tab" on each tab inside it.
An ARIA tab interface uses three roles. tablist is the container, tab is each label the user clicks, and tabpanel is the content a tab shows. The tab role describes one control, so it doesn't fit a list that holds several of them. The validator checks roles against the ARIA in HTML specification, which allows only a short set of roles on <ul>. tablist is one of them and tab isn't.
In most cases the markup has the right idea and the wrong value: role="tab" was meant to be role="tablist". As written, screen readers announce the whole list as a single tab named after all of its items. The validator usually reports a second error on the same element, because a tab must sit inside a tablist.
Make each tab a <button>, which gets keyboard focus and Enter and Space activation without extra code. Give each <li> role="presentation" to remove its list item role, so the buttons count as direct children of the tablist. If you don't need list markup, a <div role="tablist"> that holds the buttons is simpler. The roles only change what assistive technologies announce. Your script still has to show the right panel, update aria-selected, and move focus between tabs with the arrow keys.
Invalid example
<ul role="tab">
<li><a href="#overview">Overview</a></li>
<li><a href="#pricing">Pricing</a></li>
</ul>
Valid example
<ul role="tablist" aria-label="Product details">
<li role="presentation">
<button type="button" role="tab" id="tab-overview" aria-selected="true" aria-controls="panel-overview">Overview</button>
</li>
<li role="presentation">
<button type="button" role="tab" id="tab-pricing" aria-selected="false" aria-controls="panel-pricing" tabindex="-1">Pricing</button>
</li>
</ul>
<div role="tabpanel" id="panel-overview" aria-labelledby="tab-overview">
<p>A short summary of the product.</p>
</div>
<div role="tabpanel" id="panel-pricing" aria-labelledby="tab-pricing" hidden>
<p>Plans start at $10 per month.</p>
</div>
Find issues like this automatically
Rocket Validator scans thousands of pages in seconds, detecting HTML issues across your entire site.
Help us improve our guides
Was this guide helpful?
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.
1K Weekly
1,000 monthly checks. Cancel anytime.
Get 1K Weekly →Join teams across 40+ countries