References

Beginner-friendly references for web development, with live, editable examples.

The HTML aria-invalid attribute

ARIA Accessibility
In short

The aria-invalid attribute flags a field whose value failed validation, with the value true, grammar or spelling. Any other value counts as true, except false, an empty string or undefined. It runs no check and blocks no submission, which leaves the testing to your validation code.

Overview

The aria-invalid attribute reports an entered value that doesn't conform to the format the application expects. Email addresses and telephone numbers are typical cases, and it can also mark an empty required field. Typical form elements can carry it, with or without an ARIA role.

The value true means validation failed, grammar and spelling name a detected error, and false means none was detected. No attribute, an empty string or the word undefined also means false. Browsers must treat any other value as true, so aria-invalid="yes" marks the field invalid.

Its supported roles in WAI-ARIA 1.2 are application, checkbox, combobox, gridcell, listbox, radiogroup, slider, spinbutton, textbox and tree, along with the five roles that inherit it. On other roles, the use is deprecated.

Don't set it on a required widget merely because the user hasn't entered data yet. Wait until after a submit attempt, since the person may still be filling in the field.

On a valid input, aria-invalid="true" leaves validity.valid true and the form submits, since constraint validation ignores it. An empty required input with aria-invalid="false" still blocks the form. With false on a field that fails its pattern, Chrome exposes it as valid and Firefox as invalid.

Syntax

<label for="code">Order code</label>
<input id="code" name="code" value="12" aria-invalid="true">

Values

Value
false | true | grammar | spelling

Example

Live example
<form id="check">
  <label for="code">Order code</label>
  <input id="code" placeholder="AB-1234" aria-invalid="false">
  <button>Check</button>
  <p id="hint" hidden style="color:#b91c1c;margin:8px 0">Use two capitals, a hyphen and four digits.</p>
  <p id="out" role="status" style="overflow-wrap:anywhere"></p>
  <p>Press Check with the field empty or wrong, then enter AB-1234.</p>
</form>
<script>
const form = document.getElementById('check');
const code = document.getElementById('code');
const hint = document.getElementById('hint');
const out = document.getElementById('out');
form.addEventListener('submit', function (e) {
  e.preventDefault();
  const good = /^[A-Z]{2}-[0-9]{4}$/.test(code.value.trim());
  code.setAttribute('aria-invalid', String(!good));
  code.style.outline = good ? '' : '2px solid #b91c1c';
  hint.hidden = good;
  if (good) code.removeAttribute('aria-errormessage');
  else code.setAttribute('aria-errormessage', 'hint');
  out.textContent = (good ? 'aria-invalid is false and the hint is hidden and unlinked.' : 'aria-invalid is true and aria-errormessage points at the hint.') +
    ' validity.valid is ' + code.validity.valid + '.';
});
</script>

Best practices

  • Clear aria-invalid once the value passes, by setting it to false or removing it. A stale true keeps flagging a field the user has already fixed.
  • Suggest a fix when you know one, and link the text that holds it with aria-errormessage.
  • Treat the attribute as one of three parts, along with styling through [aria-invalid="true"] and a message linked by aria-errormessage.
  • Once the user has entered a value, you can check it on blur or wait for submission, though waiting isn't necessarily recommended.
  • Reach for it when you write your own validation. HTML's built-in checks show the browser's own message, which varies by browser and can't be styled.

Frequently asked questions

What do the grammar and spelling values of aria-invalid mean?
The grammar and spelling values of aria-invalid name the error detected, while true means a general failure. All three are exposed as invalid.
Does aria-invalid trigger the CSS :invalid selector?
No, :invalid follows the browser's own validation, not aria-invalid. An input with a valid value and aria-invalid=true matches :valid.
Is aria-invalid needed when a native pattern check fails?
Not for a pattern mismatch, which already maps to the invalid state with no aria-invalid in the markup.
Should aria-invalid=false be in the markup from the start?
You can set aria-invalid=false from the start, but it isn't strictly necessary. The default is false, so adding the attribute when a check fails works too.
Is aria-invalid deprecated on a button?
Yes, aria-invalid is deprecated on the button role in WAI-ARIA 1.2, though it's still exposed there. The same deprecation covers the radio role, while radiogroup still supports it.
How do aria-invalid and aria-errormessage work together?
The aria-invalid attribute flags the field, and aria-errormessage names the element holding the explanation. Set both in the same validation step.