Accessibility Change Audit
Brief purpose: review UI changes for accessibility regressions and missing improvements, then propose minimal fixes tied to the diff.
Overview
This skill audits UI diffs for semantics, keyboard access, focus management, ARIA correctness, contrast, and testability. It is diff-first: only evaluate changed lines and their immediate context.
Prerequisites
- A diff, PR, or change list that includes relevant UI files.
- Optional: a screenshot or description of the changed UI state.
Instructions
Step 1: Scope the audit to the diff
Identify changed UI elements, interactions, and styles. Ignore unrelated files.
Step 2: Run the diff-first checklist
Focus on changes that alter semantics, interaction, or visual affordances.
Step 3: Produce findings and minimal fixes
Tie each issue to a specific change and propose the smallest reasonable fix.
Step 4: Improve test reliability
Recommend role- and name-based queries for tests instead of data or class selectors.
Audit Checklist (Diff-First)
Semantics and structure
- Headings follow order and are not skipped.
- Interactive elements are buttons/links, not divs/spans.
- Landmarks are present for new regions (main, nav, header, footer, aside).
- Lists and tables use correct elements (ul/ol/li, th/thead/tbody).
Labels and names
- Inputs have labels or aria-label/aria-labelledby.
- Icon-only controls have accessible names.
- Helper text ties to inputs via aria-describedby.
Keyboard and focus
- All interactive elements are keyboard reachable and operable.
- Focus order follows DOM order (avoid tabIndex > 0).
- Dialogs/menus trap focus and return focus to trigger.
ARIA correctness
- ARIA only when native semantics are insufficient.
- aria-expanded/controls/pressed reflect actual state.
- role is correct and not redundant.
Visual and motion
- Text and focus indicators meet contrast requirements.
- Color is not the only indicator.
- Motion respects reduced-motion preferences.
Media and imagery
- Images have meaningful alt or empty alt for decorative.
- Media controls are accessible and labeled.
Testing reliability
- New elements can be found by role and accessible name.
- Interaction tests use user flows and semantic queries.
Minimal Fix Patterns
- Icon-only button
- Add visible text or aria-label.
- Clickable non-button
- Convert to or add role="button", tabIndex=0, and Enter/Space handling.
- Form label
- Add or aria-labelledby and connect helper text with aria-describedby.
- Disclosure
- Toggle uses aria-expanded and aria-controls; update on state change.
- Dialog
- Use role="dialog", aria-modal, label by heading, and return focus on close.
Output Format
Findings (ordered by severity):
- [severity] path:line - problem and impact
Fix: minimal change suggestion
Tests:
- Recommend updates that use role/name queries and user-driven events.
UX/Speed Note:
- Call out any change that impacts perceived speed (layout shifts, heavy DOM, over-rendering).
Severity scale: blocker, high, medium, low.
Example Review Output
Findings:
- high
packages/web/src/views/Example.tsx:42 - Clickable div lacks keyboard support; keyboard users cannot activate it.
Fix: convert to or add role, tabIndex, and Enter/Space handlers.
- medium
packages/web/src/views/Example.tsx:60 - Icon-only control has no accessible name.
Fix: add aria-label="Add event".
Tests:
- Add a role-based query: getByRole("button", { name: /add event/i }).
UX/Speed Note:
- No layout shift detected; DOM complexity unchanged.
1---2name: codex-a11y-audit3description: Use when reviewing UI diffs, accessibility audits, or flaky UI tests to catch a11y regressions, semantic issues, keyboard/focus problems, and to recommend minimal fixes plus role-based test selectors.4---5
6# Accessibility Change Audit
7
8Brief purpose: review UI changes for accessibility regressions and missing improvements, then propose minimal fixes tied to the diff.
9
10## Overview
11
12This skill audits UI diffs for semantics, keyboard access, focus management, ARIA correctness, contrast, and testability. It is diff-first: only evaluate changed lines and their immediate context.
13
14## Prerequisites
15
16- A diff, PR, or change list that includes relevant UI files.
17- Optional: a screenshot or description of the changed UI state.
18
19## Instructions
20
21### Step 1: Scope the audit to the diff
22
23Identify changed UI elements, interactions, and styles. Ignore unrelated files.
24
25### Step 2: Run the diff-first checklist
26
27Focus on changes that alter semantics, interaction, or visual affordances.
28
29### Step 3: Produce findings and minimal fixes
30
31Tie each issue to a specific change and propose the smallest reasonable fix.
32
33### Step 4: Improve test reliability
34
35Recommend role- and name-based queries for tests instead of data or class selectors.
36
37## Audit Checklist (Diff-First)
38
39Semantics and structure
40
41- Headings follow order and are not skipped.
42- Interactive elements are buttons/links, not divs/spans.
43- Landmarks are present for new regions (main, nav, header, footer, aside).
44- Lists and tables use correct elements (ul/ol/li, th/thead/tbody).
45
46Labels and names
47
48- Inputs have labels or aria-label/aria-labelledby.
49- Icon-only controls have accessible names.
50- Helper text ties to inputs via aria-describedby.
51
52Keyboard and focus
53
54- All interactive elements are keyboard reachable and operable.
55- Focus order follows DOM order (avoid tabIndex > 0).
56- Dialogs/menus trap focus and return focus to trigger.
57
58ARIA correctness
59
60- ARIA only when native semantics are insufficient.
61- aria-expanded/controls/pressed reflect actual state.
62- role is correct and not redundant.
63
64Visual and motion
65
66- Text and focus indicators meet contrast requirements.
67- Color is not the only indicator.
68- Motion respects reduced-motion preferences.
69
70Media and imagery
71
72- Images have meaningful alt or empty alt for decorative.
73- Media controls are accessible and labeled.
74
75Testing reliability
76
77- New elements can be found by role and accessible name.
78- Interaction tests use user flows and semantic queries.
79
80## Minimal Fix Patterns
81
821. Icon-only button
83
84- Add visible text or aria-label.
85
862. Clickable non-button
87
88- Convert to <button> or add role="button", tabIndex=0, and Enter/Space handling.
89
903. Form label
91
92- Add <label htmlFor> or aria-labelledby and connect helper text with aria-describedby.
93
944. Disclosure
95
96- Toggle uses aria-expanded and aria-controls; update on state change.
97
985. Dialog
99
100- Use role="dialog", aria-modal, label by heading, and return focus on close.
101
102## Output Format
103
104Findings (ordered by severity):
105
106- [severity] path:line - problem and impact
107 Fix: minimal change suggestion
108
109Tests:
110
111- Recommend updates that use role/name queries and user-driven events.
112
113UX/Speed Note:
114
115- Call out any change that impacts perceived speed (layout shifts, heavy DOM, over-rendering).
116
117Severity scale: blocker, high, medium, low.
118
119## Example Review Output
120
121Findings:
122
123- high `packages/web/src/views/Example.tsx:42` - Clickable div lacks keyboard support; keyboard users cannot activate it.
124 Fix: convert to <button type="button"> or add role, tabIndex, and Enter/Space handlers.
125- medium `packages/web/src/views/Example.tsx:60` - Icon-only control has no accessible name.
126 Fix: add aria-label="Add event".
127
128Tests:
129
130- Add a role-based query: getByRole("button", { name: /add event/i }).
131
132UX/Speed Note:
133
134- No layout shift detected; DOM complexity unchanged.