Perform comprehensive WCAG accessibility audits on web components. Use when auditing accessibility, checking a11y compliance, or reviewing UI for keyboard/screen reader support.
Install
mkdir -p .claude/skills/accessibility-audit && curl -L -o skill.zip "https://agentskills.codes/api/skills/download/15860" && unzip -o skill.zip -d .claude/skills/accessibility-audit && rm skill.zipInstalls to .claude/skills/accessibility-audit
Activation
This is the description your AI agent reads to decide when to run this skill — the better it matches your request, the more reliably it fires.
Perform comprehensive WCAG accessibility audits on web components. Use when auditing accessibility, checking a11y compliance, or reviewing UI for keyboard/screen reader support.177 chars✓ has a “when” trigger
About this skill
Accessibility Audit Skill
Perform comprehensive WCAG 2.2 accessibility audits on web components and applications.
Quick Start
import axe from 'axe-core';
// Run accessibility audit on entire page
const results = await axe.run();
// Run on specific element
const results = await axe.run(document.querySelector('#main'));
// Run with specific WCAG rules
const results = await axe.run(document, {
runOnly: { type: 'tag', values: ['wcag2aa', 'wcag21aa'] },
});
Skill Contents
Documentation
docs/wcag-guidelines.md- WCAG 2.2 levels and success criteriadocs/aria-patterns.md- Common ARIA patterns and rolesdocs/screen-readers.md- Screen reader testing guidedocs/testing-tools.md- Accessibility testing tools and setup
Examples
examples/axe-tests.ts- Vitest integration with axe-coreexamples/component-audit.tsx- Accessible React component auditexamples/keyboard-navigation.ts- Keyboard interaction patterns
Templates
templates/audit-report.md- Accessibility audit report templatetemplates/checklist.md- WCAG compliance checklist
Reference
REFERENCE.md- Quick reference cheatsheet
WCAG 2.2 Compliance Levels
| Level | Target Audience | Requirements |
|---|---|---|
| A | Minimum | Essential accessibility features |
| AA | Standard (Recommended) | Removes significant barriers |
| AAA | Enhanced | Highest level of accessibility |
Note: Most organizations target WCAG 2.2 Level AA compliance.
Comprehensive Audit Checklist
1. Perceivable
Text Alternatives (1.1)
- Images have descriptive
alttext - Decorative images have
alt="" - Complex images have extended descriptions
- Icon-only buttons have
aria-label - SVGs have
role="img"and accessible names
Time-Based Media (1.2)
- Videos have captions
- Videos have audio descriptions (if needed)
- Live audio has captions (AA)
Adaptable (1.3)
- Headings follow logical hierarchy (
<h1>→<h6>) - Lists use proper
<ul>,<ol>,<dl>elements - Tables have
<th>andscopeattributes - Form inputs have associated
<label>elements - Reading order is logical without CSS
- Instructions don't rely solely on sensory characteristics
Distinguishable (1.4)
- Color is not the only means of conveying information
- Text contrast ratio ≥ 4.5:1 (normal) or 3:1 (large)
- UI component contrast ≥ 3:1
- Text can resize to 200% without loss of content
- Images of text are avoided (except logos)
- Content reflows at 320px width without horizontal scroll
- Non-text contrast meets 3:1 ratio
- Text spacing can be adjusted without breaking layout
2. Operable
Keyboard Accessible (2.1)
- All functionality available via keyboard
- No keyboard traps (except modals with escape)
- Character key shortcuts can be disabled/remapped
Enough Time (2.2)
- Time limits can be adjusted or extended
- Moving content can be paused/stopped
- No content flashes more than 3 times per second
Navigable (2.4)
- Skip links provided for repeated blocks
- Pages have descriptive
<title> - Focus order is logical
- Link purpose is clear from text (or context)
- Multiple ways to navigate site (search, sitemap, nav)
- Headings and labels are descriptive
- Focus indicator is visible (enhanced in 2.2)
Input Modalities (2.5)
- Pointer gestures have single-pointer alternatives
- Touch targets are at least 24×24px (44×44px recommended)
- Dragging has non-dragging alternative
- Motion actuation can be disabled
3. Understandable
Readable (3.1)
- Page language declared (
<html lang="en">) - Language changes marked (
<span lang="fr">)
Predictable (3.2)
- Focus doesn't trigger unexpected changes
- Input doesn't trigger unexpected changes
- Navigation is consistent across pages
- Components are identified consistently
Input Assistance (3.3)
- Errors are identified and described
- Labels or instructions provided for inputs
- Error suggestions are provided
- Error prevention for legal/financial data
- Redundant entry assistance (new in 2.2)
- Accessible authentication (new in 2.2)
4. Robust
Compatible (4.1)
- HTML validates (no duplicate IDs)
- Name, role, value available for custom controls
- Status messages use
aria-liveregions
Automated Testing Setup
Vitest + axe-core
// vitest.setup.ts
import 'vitest-axe/extend-expect';
// Component test
import { render } from '@testing-library/react';
import { axe } from 'vitest-axe';
test('component is accessible', async () => {
const { container } = render(<MyComponent />);
const results = await axe(container);
expect(results).toHaveNoViolations();
});
Playwright + axe-core
// e2e/accessibility.spec.ts
import { test, expect } from '@playwright/test';
import AxeBuilder from '@axe-core/playwright';
test('page has no accessibility violations', async ({ page }) => {
await page.goto('/');
const results = await new AxeBuilder({ page })
.withTags(['wcag2a', 'wcag2aa', 'wcag21aa', 'wcag22aa'])
.analyze();
expect(results.violations).toEqual([]);
});
Common ARIA Patterns
Button
<!-- Native button (preferred) -->
<button type="button">Click me</button>
<!-- Custom button -->
<div role="button" tabindex="0" aria-pressed="false">Toggle</div>
Dialog/Modal
<div role="dialog" aria-modal="true" aria-labelledby="dialog-title">
<h2 id="dialog-title">Confirm Action</h2>
<p>Are you sure you want to proceed?</p>
<button>Confirm</button>
<button>Cancel</button>
</div>
Tabs
<div role="tablist" aria-label="Main sections">
<button role="tab" aria-selected="true" aria-controls="panel-1">Tab 1</button>
<button
role="tab"
aria-selected="false"
aria-controls="panel-2"
tabindex="-1"
>
Tab 2
</button>
</div>
<div role="tabpanel" id="panel-1" aria-labelledby="tab-1">Content 1</div>
<div role="tabpanel" id="panel-2" aria-labelledby="tab-2" hidden>Content 2</div>
Live Regions
<!-- Polite announcement (waits for silence) -->
<div aria-live="polite" aria-atomic="true">3 items added to cart</div>
<!-- Assertive announcement (interrupts) -->
<div aria-live="assertive" role="alert">Error: Invalid email address</div>
<!-- Status message -->
<div role="status">Loading complete</div>
Keyboard Navigation Requirements
| Component | Keys | Behavior |
|---|---|---|
| Button | Enter, Space | Activate |
| Link | Enter | Navigate |
| Checkbox | Space | Toggle |
| Radio Group | ← → ↑ ↓ | Move selection |
| Tabs | ← → | Switch tabs |
| Menu | ↑ ↓ Enter Esc | Navigate, select, close |
| Modal | Tab Esc | Trap focus, close |
| Combobox | ↑ ↓ Enter Esc | Navigate, select, close |
| Slider | ← → | Adjust value |
Color Contrast Requirements
| Element Type | AA Ratio | AAA Ratio |
|---|---|---|
| Normal text (<18px) | 4.5:1 | 7:1 |
| Large text (≥18px or 14px bold) | 3:1 | 4.5:1 |
| UI components & graphics | 3:1 | N/A |
| Focus indicators | 3:1 | N/A |
Checking Contrast
// Using axe-core
axe.run(document, {
rules: { 'color-contrast': { enabled: true } },
});
/* CSS for ensuring focus visibility */
:focus-visible {
outline: 2px solid #0066cc;
outline-offset: 2px;
}
Audit Output Format
When asked to "audit accessibility", output a report:
# Accessibility Audit Report
**URL/Component**: [Identifier]
**Date**: [YYYY-MM-DD]
**Auditor**: [Name]
**WCAG Version**: 2.2 Level AA
**Tools Used**: axe-core, WAVE, VoiceOver/NVDA
## Executive Summary
- **Total Issues**: X
- **Critical**: X | **Serious**: X | **Moderate**: X | **Minor**: X
- **Compliance Status**: Pass / Fail / Partial
## Issues Found
### Issue 1: [WCAG Criterion] - [Impact Level]
**Element**: `<selector or description>`
**WCAG**: X.X.X (Level A/AA/AAA)
**Impact**: Critical / Serious / Moderate / Minor
**Problem**:
[Description of the accessibility barrier]
**Affected Users**:
- [ ] Screen reader users
- [ ] Keyboard users
- [ ] Low vision users
- [ ] Cognitive disabilities
**Remediation**:
- <div onclick="submit()">Submit</div>
* <button type="submit">Submit</button>
**Resources**:
- [Link to WCAG success criterion]
- [Link to technique]
## Testing Results
### Automated Testing
- axe-core: X violations
- Lighthouse: XX% accessibility score
### Manual Testing
- [ ] Keyboard navigation tested
- [ ] Screen reader tested (VoiceOver/NVDA)
- [ ] Zoom 200% tested
- [ ] Color contrast verified
- [ ] Motion preferences tested
## Recommendations
1. [Priority 1 fix]
2. [Priority 2 fix]
3. [Priority 3 fix]
Commands
# Run automated accessibility tests
npm run test:a11y
# Run Lighthouse accessibility audit
npx lighthouse <url> --only-categories=accessibility
# Generate detailed report
npm run audit:a11y -- --output=report.json
Screen Reader Testing
macOS VoiceOver
- Enable:
Cmd + F5 - Navigate:
Ctrl + Option + Arrow Keys - Read all:
Ctrl + Option + A - Rotor:
Ctrl + Option + U
Windows NVDA
- Enable:
Ctrl + Alt + N - Navigate:
Tab,Arrow Keys - Read al
Content truncated.