agentsclimarketplace

Axe rules

Skill mgifford/accessibility-skills/skills/axe-rules

Load this skill when configuring axe-core scans, reviewing automated accessibility test results, or writing tests that use @axe-core/playwright, @axe-core/react, or similar integrations. Provides a quick reference to axe 4.x rule IDs, their WCAG mapping, and default severity levels.From its SKILL.md

Install
npx -y skills add mgifford/accessibility-skills --skill axe-rules

Assembled from the repository path, not quoted from the project. Check it against their README if it does not work.

SKILL.md

11.5 KB, ~2.9k tokens by cl100k_base, as published. Nobody here has run it

Axe-Core Rules Reference Skill

Canonical source: examples/AXE_RULES_REFERENCE.md and examples/AXE_RULES_COVERAGE.md in mgifford/ACCESSIBILITY.md This skill is derived from those files. When in doubt, the example is authoritative. Note: the canonical files are organized around a specific test-fixture scanner project (numbered test pages). This skill re-presents the same rule set and severities as a general-purpose reference, independent of any particular fixture.

Apply these rules when writing, reviewing, or debugging axe-core scans.


Core Principle

Axe-core catches ~30–40% of WCAG issues automatically. It is the baseline, not the ceiling. Always pair automated scanning with manual keyboard and screen reader testing.

An axe-core result is evidence, not a conformance decision. Preserve the rule's raw outcome (violations, incomplete, passes, inapplicable) exactly as axe reports it — do not overwrite or discard it when converting to a project finding. Cite this file, AXE_RULES_REFERENCE.md, or the rule's own dequeuniversity.com/rules/axe/ page as the authority for a WCAG mapping; do not invent a mapping axe-core does not document for that rule. Record an unreviewed violations result as evidence_status: automated-indicator with handling: review — never as a confirmed standards failure — until a human confirms it. See Accessibility Finding Tracking: Policy Classification.

Key tags to include in scans:

.withTags(['wcag2a', 'wcag2aa', 'wcag21aa', 'wcag22aa'])

Axe-core 4.11 includes 100+ automated checks across these categories: WCAG 2.0 A/AA (68 rules), WCAG 2.1 A/AA (26 rules), WCAG 2.2 A/AA (1 rule, disabled by default), Best Practices (30+ rules), WCAG AAA (3 rules, disabled by default), Experimental (9 rules, disabled by default), and Deprecated (7 rules, disabled by default).


Severity Scale (axe-core)

axe severityMeaning
criticalBlocks access for one or more disability groups
seriousSignificantly impairs access
moderateCreates friction; workaround exists
minorBest-practice gap; marginal impact

Critical Rules — must never appear in production

Rule IDCategoryDescription
image-altText alternatives<img> missing alt attribute
area-altText alternativesImage map <area> missing alt text
input-image-altText alternatives<input type="image"> missing alt
video-captionText alternatives<video> without captions
aria-allowed-attrARIAElement has unsupported ARIA attributes for its role
aria-hidden-bodyARIAaria-hidden applied to <body>
aria-required-attrARIARequired ARIA attribute missing
aria-required-childrenARIARequired child ARIA roles missing
aria-required-parentARIARequired parent ARIA role missing
aria-rolesARIAInvalid ARIA role value
aria-valid-attrARIAInvalid ARIA attribute name
aria-valid-attr-valueARIAARIA attribute has invalid value
labelFormsForm input without associated <label>
select-nameForms<select> without accessible name
button-nameButtons/LinksButton without discernible text
input-button-nameButtons/Links<input type="button"> without text
duplicate-id-ariaStructureDuplicate id values referenced by ARIA
meta-refreshMeta<meta http-equiv="refresh"> causes timed redirect

Serious Rules — fix before release

Rule IDCategoryDescription
object-altText alternatives<object> without accessible text
svg-img-altText alternativesSVG with role="img" and no accessible name
role-img-altText alternativesElement with role="img" lacks alt text
aria-braille-equivalentARIABraille label without non-braille equivalent
aria-command-nameARIAButton, link, or menu item without accessible name
aria-conditional-attrARIAARIA attribute used contrary to role spec
aria-hidden-focusARIAaria-hidden element contains focusable content
aria-input-field-nameARIAARIA input field without accessible name
aria-meter-nameARIAARIA meter element without accessible name
aria-progressbar-nameARIAARIA progressbar element without accessible name
aria-prohibited-attrARIAProhibited ARIA attribute used
aria-toggle-field-nameARIAARIA toggle field without accessible name
aria-tooltip-nameARIAARIA tooltip without accessible name
aria-dialog-nameARIADialog without accessible name
aria-treeitem-nameARIATree item without accessible name
color-contrastColorText contrast below 4.5:1 (normal) or 3:1 (large)
frame-titleFrames<iframe> without accessible name
frame-title-uniqueFramesFrame titles are not unique
frame-focusable-contentFramesFrame with focusable content is tabindex="-1"
html-has-langLanguage<html> missing lang attribute
html-lang-validLanguagelang attribute has invalid BCP 47 value
valid-langLanguageInline lang value is invalid
document-titleLanguage<title> element missing
listStructure<ul>/<ol> contains elements other than <li>
listitemStructure<li> outside <ul> or <ol>
definition-listStructure<dl> contains elements other than <dt>/<dd>
dlitemStructure<dt>/<dd> outside <dl>
bypassKeyboardNo skip navigation mechanism present
scrollable-region-focusableKeyboardScrollable region not keyboard accessible
link-nameButtons/LinksLink without discernible text
link-in-text-blockButtons/LinksLink not distinguishable from surrounding text
avoid-inline-spacingContent sizingText spacing overrides not adjustable
autocomplete-validFormsautocomplete attribute invalid or missing
tabindexBest practicestabindex value > 0 used
label-title-onlyBest practicesForm field labeled only via title attribute
label-content-name-mismatchBest practices (experimental)Visible label text doesn't match accessible name
td-has-headerTables (experimental)Large table cells lack associated headers
table-fake-captionTables (experimental)Table caption not marked up with <caption>
p-as-headingBest practices (experimental)Paragraph styled to look like a heading

Moderate Rules — fix in near-term backlog

Rule IDCategoryDescription
heading-orderHeadingsHeading levels skipped (e.g., h1 → h3)
empty-headingHeadingsHeading has no discernible text
th-has-data-cellsTablesTable headers have no associated data cells
td-headers-attrTablesTable cells reference invalid header IDs
meta-viewportMetaViewport user-scalable=no disables zoom
html-xml-lang-mismatchLanguagelang and xml:lang attributes disagree
form-field-multiple-labelsFormsForm field has multiple conflicting labels
landmark-one-mainBest practicesPage has no <main> landmark
landmark-banner-is-top-levelBest practicesbanner landmark not at top level
landmark-contentinfo-is-top-levelBest practicescontentinfo landmark not at top level
landmark-main-is-top-levelBest practicesmain landmark not at top level
landmark-no-duplicate-bannerBest practicesMore than one banner landmark
landmark-no-duplicate-contentinfoBest practicesMore than one contentinfo landmark
landmark-no-duplicate-mainBest practicesMore than one main landmark
regionBest practicesContent exists outside landmark regions
page-has-heading-oneBest practicesPage has no <h1>
scope-attr-validBest practicesscope attribute has invalid value
accesskeysBest practicesaccesskey values are not unique

Minor Rules

Rule IDCategoryDescription
table-duplicate-nameTables<caption> text duplicates summary attribute
aria-deprecated-roleARIADeprecated ARIA role used
server-side-image-mapKeyboardServer-side image map used
aria-textARIA (best practice)role="text" on an element with focusable descendants

Disabled-by-default rules (deprecated marquee/blink/audio-caption) are not listed above — flag them if encountered, but they are not enabled in a default scan.

The three WCAG AAA rules axe-core disables by default report against a level the project's AA target does not require. If enabled and a project has not declared a broader target, classify a confirmed finding from one of these rules as obligation: aspirational, not advisory — it is still a real AAA-level finding, just not part of the AA baseline. Do not report satisfying one of these rules as WCAG AAA conformance.


Running axe-core in CI (Playwright)

import { test, expect } from '@playwright/test';
import AxeBuilder from '@axe-core/playwright';

test('No WCAG 2.x AA violations', async ({ page }) => {
  await page.goto('/');
  const results = await new AxeBuilder({ page })
    .withTags(['wcag2a', 'wcag2aa', 'wcag21aa', 'wcag22aa'])
    .analyze();
  expect(results.violations).toEqual([]);
});

Common configuration options:

// Exclude a specific element (use sparingly — document the reason)
.exclude('#known-false-positive')

// Include only a specific element
.include('#component-under-test')

// Disable a specific rule (document the reason and JIRA/issue link)
.disableRules(['color-contrast'])

Definition of Done Checklist

  • axe-core scans run on every PR with wcag2a, wcag2aa, wcag21aa, wcag22aa tags
  • Zero critical violations in production code
  • Zero serious violations in production code (or explicit waiver with issue link)
  • All rule exclusions documented with reason and associated issue
  • Light and dark colour schemes both tested
  • Mobile viewport tested
  • axe results published as CI artifact for reference

Key WCAG Criteria (automation coverage)

  • 1.1.1 Non-text Content (A)
  • 1.3.1 Info and Relationships (A)
  • 1.4.3 Contrast Minimum (AA)
  • 2.4.2 Page Titled (A)
  • 3.1.1 Language of Page (A)
  • 4.1.2 Name, Role, Value (A)
  • 4.1.3 Status Messages (AA) — partial coverage

Automation covers ~30–40% of WCAG issues. Always pair with manual testing.


References

Standards horizon: These rules target WCAG 2.2 AA. Monitor: https://www.w3.org/TR/wcag-3.0/

What ships with it: 1 file

1.8 KB alongside SKILL.md

Keep looking

Skills are one crate of 325,949. Ordering is by how many stacks a row turns up in, so the top of any crate is what has actually been picked rather than what has the most stars.