HTML Guides for href
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.
An <a> element with an href attribute is interactive content, and interactive content cannot appear inside another <a> element.
The href attribute is what triggers this error. A link that points somewhere is interactive, and the HTML specification does not allow one interactive element to contain another. The outer <a> is already interactive, so a second linked <a> nested anywhere inside it, even several elements deep, makes the markup invalid. An <a> without href is just a placeholder and is allowed inside a link, which is why the validator names the attribute explicitly.
When links overlap like this, browsers cannot tell which destination a click should follow, and most will silently close the outer link before the inner one, producing a DOM that no longer matches your source. Screen readers run into the same ambiguity and may announce the wrong link or skip one entirely.
The fix is to give each link its own space so that no <a href> sits inside another <a href>.
Invalid example
<ahref="/products">
Browse our <ahref="/products/new">new arrivals</a> today
</a>
Valid example
<p>
<ahref="/products">Browse our products</a> or check out our
<ahref="/products/new">new arrivals</a> today.
</p>
An <a> element cannot be placed inside a <button> element because interactive content must not be nested within other interactive content.
The HTML specification forbids nesting clickable elements inside other clickable elements. Both <a> and <button> are interactive content, meaning they each expect to receive user interaction independently. When you nest one inside the other, browsers can't determine which element should handle the click, leading to unpredictable behavior and accessibility problems.
Screen readers and keyboard navigation also struggle with nested interactive elements. A user tabbing through the page may not be able to reach or activate the inner link, or may trigger the wrong action entirely.
To fix this, you have two main options: use a styled <a> element that looks like a button, or use a <button> with JavaScript to handle navigation.
Invalid Example
<button>
<ahref="/dashboard">Go to Dashboard</a>
</button>
Fixed Examples
Option 1: Style the link as a button
This is the preferred approach when the purpose is navigation.
<ahref="/dashboard"class="btn">Go to Dashboard</a>
<style>
.btn{
display: inline-block;
padding:8px16px;
background-color:#007bff;
color:#fff;
text-decoration: none;
border-radius:4px;
border: none;
cursor: pointer;
}
</style>
Option 2: Use a button with JavaScript
This works when you need button semantics but also want navigation.
<buttontype="button"onclick="location.href='/dashboard'">
Go to Dashboard
</button>
Option 1 is generally better for navigation because <a> elements communicate the correct intent to assistive technologies and allow standard browser behaviors like right-click "Open in new tab."
The <a> element with an href attribute is one of HTML's most fundamental interactive elements. Browsers and assistive technologies inherently recognize it as a link — it's focusable via the Tab key, activatable with Enter, and announced as "link" by screen readers. This built-in behavior is part of the element's implicit ARIA role, which is link.
When you explicitly add role="link" to an <a href="..."> element, you're telling assistive technologies something they already know. The W3C validator flags this as unnecessary because it violates the principle of not redundantly setting ARIA roles that match an element's native semantics. This principle is codified in the first rule of ARIA use: "If you can use a native HTML element or attribute with the semantics and behavior you require already built in, instead of re-purposing an element and adding an ARIA role, state or property to make it accessible, then do so."
While a redundant role="link" won't typically break anything, it creates noise in your markup. It can also signal to other developers that the role is necessary, leading to confusion or cargo-cult patterns. Clean, semantic HTML that relies on native roles is easier to maintain and less error-prone.
The role="link" attribute is legitimately useful when a non-interactive element like a <span> or <div> needs to behave as a link. In that case, you must also manually implement keyboard interaction (focus via tabindex, activation via Enter key handling) and provide an accessible name. But when you already have a proper <a> element with href, all of that comes for free — no ARIA needed.
Examples
❌ Incorrect: redundant role="link" on an anchor
<ahref="/about"role="link">About Us</a>
The role="link" is redundant here because the <a> element with href already has an implicit role of link.
✅ Correct: anchor without redundant role
<ahref="/about">About Us</a>
Simply remove the role="link" attribute. The browser and assistive technologies already treat this as a link.
✅ Correct: using role="link" on a non-semantic element (when necessary)
<spanrole="link"tabindex="0"onclick="location.href='/about'"onkeydown="if(event.key==='Enter')location.href='/about'">
About Us
</span>
This is the legitimate use case for role="link" — when you cannot use a native <a> element and need to make a non-interactive element behave like a link. Note the additional work required: tabindex="0" for keyboard focusability, a click handler, and a keydown handler for Enter key activation. Using a proper <a> element avoids all of this extra effort.
❌ Incorrect: multiple anchors with redundant roles
<nav>
<ahref="/"role="link">Home</a>
<ahref="/products"role="link">Products</a>
<ahref="/contact"role="link">Contact</a>
</nav>
✅ Correct: clean navigation without redundant roles
<nav>
<ahref="/">Home</a>
<ahref="/products">Products</a>
<ahref="/contact">Contact</a>
</nav>
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