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.