ADAGuard home

4 Accessibility Mistakes AI Coding Assistants Make, and How to Catch Them

AI coding assistants write components fast, and they repeat the accessibility mistakes common in the code they learned from — clickable divs with no keyboard support, aria-labels that don't match the visible text, placeholder-only inputs and removed focus outlines. Here is each mistake, the WCAG criterion it fails and how to catch it in review.

Giriprasad Patil · · 3 min read
On this page · 5 sections
  1. 1. A clickable div with no keyboard support (WCAG 2.1.1, 4.1.2)
  2. 2. An aria-label that doesn't match the visible text (WCAG 2.5.3)
  3. 3. A placeholder used as the label (WCAG 3.3.2, 1.3.1)
  4. 4. Focus outlines removed (WCAG 2.4.7)
  5. Catching these in review

AI coding assistants are good at producing working components quickly. They learned from a huge amount of public code, and public code is full of accessibility mistakes — so the same mistakes come back in generated components, looking clean and passing a quick visual review.

Here are four that show up often, the WCAG criterion each one fails, and how to catch them before they merge.

1. A clickable div with no keyboard support (WCAG 2.1.1, 4.1.2)

Ask for "a clickable card" or "a custom button" and you'll often get this:

[ JSX ]
// Works with a mouse. A keyboard user can't reach it or activate it.
<div className="btn" onClick={save}>Save</div>

Adding role="button" alone doesn't fix it: the element still isn't in the tab order and doesn't respond to Enter or Space.

[ JSX ]
// Fix: use the element that already does all of this.
<button type="button" className="btn" onClick={save}>Save</button>

A `` is focusable, activates on Enter and Space, and is announced as a button. Reach for role and tabIndex only when no native element fits.

2. An aria-label that doesn't match the visible text (WCAG 2.5.3)

Assistants like adding aria-label "for accessibility", often with a more descriptive phrase than the button shows:

[ HTML ]
<!-- Visible text "Buy now"; accessible name "Add product to basket" -->
<button aria-label="Add product to basket">Buy now</button>

The aria-label replaces the visible text as the accessible name. A voice-control user who says "click Buy now" gets nothing, because no control is called "Buy now". WCAG 2.5.3 (Label in Name) requires the accessible name to contain the visible label.

[ HTML ]
<!-- Fix: let the visible text be the name -->
<button>Buy now</button>

If you need more context for screen reader users, keep the visible words at the start of the name: aria-label="Buy now: Linen shirt".

3. A placeholder used as the label (WCAG 3.3.2, 1.3.1)

[ HTML ]
<input type="email" placeholder="Email address">

The placeholder disappears as soon as someone starts typing, it's usually low contrast, and it isn't a reliable label. Give every input a visible, associated label:

[ HTML ]
<label for="email">Email address</label>
<input id="email" type="email" autocomplete="email">

4. Focus outlines removed (WCAG 2.4.7)

Generated CSS often includes a reset like this:

[ CSS ]
*:focus { outline: none; }

It removes the only sign of where a keyboard user is on the page. If the default ring doesn't fit the design, replace it rather than removing it, and keep it to keyboard focus:

[ CSS ]
:focus-visible {
  outline: 2px solid currentColor;
  outline-offset: 2px;
}

Catching these in review

Each check below catches a different subset, so use more than one:

  • A linter in the editor. eslint-plugin-jsx-a11y flags click handlers on non-interactive elements and inputs without labels while you type.
  • Prefer native elements in prompts and review. Asking the assistant for "a ``" or "a native " gets better output than "a clickable element".
  • A keyboard pass. Tab through the new component. If you can't reach or operate it, it fails.
  • A check of the rendered page. Mistakes 1, 2 and 4 depend on the rendered page — computed names, focus styles, what's focusable. ADAGuard loads the page in a real browser and checks those, including label-in-name. Scan a page free.

Avoid "fix it at runtime" scripts as the safety net. A script that edits the page in each visitor's browser leaves the source unchanged, so every mistake is still in the code the assistant learned from your repo. See why overlays don't fix accessibility.

AI assistants are useful here too: once a failure is found, they're good at applying a known fix across many files. The part they can't do is notice that a component they just wrote doesn't work with a keyboard. That takes a test.

Keep reading