How to fix nested interactive on Headless / Custom (I build in code)

Remove or restructure nested interactive elements so that no focusable control (button, link, input, etc.) is placed inside another interactive control, and never rely on tabindex="-1" or aria-hidden="true" to hide an inner interactive element from assistive technologies.

Steps for Headless / Custom (I build in code)

  1. Search your component codebase for patterns where interactive HTML elements are children of other interactive elements: `<a><button`, `<button><a`, `<a><input`, `<button><select`, etc. Use grep or your IDE's global search.
  2. Refactor each component: decide which element is the primary interactive control, keep it, and replace the other with a non-interactive element (`<span>`, `<div>`, `<svg aria-hidden='true'>`) that is styled to look identical.
  3. Remove any tabindex='-1' or aria-hidden='true' that was masking the inner element — these are not reliable fixes and are no longer needed.
  4. Add a lint rule (e.g., eslint-plugin-jsx-a11y rule 'no-interactive-element-to-noninteractive-role' and 'interactive-supports-focus') to your CI pipeline to catch regressions automatically.
  5. Run axe-core or Playwright accessibility checks in your test suite against the affected pages to confirm zero nested-interactive violations before merging.
Official Headless / Custom (I build in code) documentation ↗

What is nested interactive?

WCAG Success Criterion 4.1.2 requires that every user interface component has a name, role, and value that assistive technologies (like screen readers) can reliably understand. A "nested interactive" violation occurs when one interactive element — such as a `<button>`, `<a>`, `<select>`, or `<input>` — is placed inside another interactive element in the HTML. For example, putting a `<button>` inside an `<a>` tag, or an `<a>` link inside a `<button>`. HTML forbids this nesting, browsers handle it inconsistently, and screen readers and keyboard navigation can behave unpredictably. Adding `tabindex="-1"` or `aria-hidden="true"` to the inner element does NOT reliably hide it from assistive technology — screen readers can still discover and announce it, creating a confusing or broken experience.

Keyboard-only users and screen-reader users (a significant and legally protected segment of shoppers) can get stuck, confused, or blocked from completing a purchase when interactive controls are nested. In many jurisdictions — including the US (ADA), EU (EN 301 549), and UK (Equality Act) — inaccessible ecommerce stores face real legal exposure including complaints, audits, and lawsuits. Beyond legal risk, a broken checkout button or unclickable product link directly costs you conversions and revenue. Google also uses accessibility signals as a quality indicator, so fixing these issues can modestly improve crawlability and organic rankings over time.

See the complete Nested interactive guide for every platform and the full background.

Not sure if your Headless / Custom (I build in code) store has this?

Run a free SEOLZ scan — we’ll find nested interactive and every other issue across your whole site.

Scan my site free

Fix nested interactive on another platform