locus-product-planning 1.2.0 → 1.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (65) hide show
  1. package/LICENSE +21 -21
  2. package/agents/engineering/architect-reviewer.md +122 -122
  3. package/agents/engineering/engineering-manager.md +101 -101
  4. package/agents/engineering/principal-engineer.md +98 -98
  5. package/agents/engineering/staff-engineer.md +86 -86
  6. package/agents/engineering/tech-lead.md +114 -114
  7. package/agents/executive/ceo-strategist.md +81 -81
  8. package/agents/executive/cfo-analyst.md +97 -97
  9. package/agents/executive/coo-operations.md +100 -100
  10. package/agents/executive/cpo-product.md +104 -104
  11. package/agents/executive/cto-architect.md +90 -90
  12. package/agents/product/product-manager.md +70 -70
  13. package/agents/product/project-manager.md +95 -95
  14. package/agents/product/qa-strategist.md +132 -132
  15. package/agents/product/scrum-master.md +70 -70
  16. package/dist/index.cjs +13012 -0
  17. package/dist/index.cjs.map +1 -0
  18. package/dist/{lib/skills-core.d.ts → index.d.cts} +46 -12
  19. package/dist/index.d.ts +113 -5
  20. package/dist/index.js +12963 -237
  21. package/dist/index.js.map +1 -0
  22. package/package.json +88 -82
  23. package/skills/01-executive-suite/ceo-strategist/SKILL.md +132 -132
  24. package/skills/01-executive-suite/cfo-analyst/SKILL.md +187 -187
  25. package/skills/01-executive-suite/coo-operations/SKILL.md +211 -211
  26. package/skills/01-executive-suite/cpo-product/SKILL.md +231 -231
  27. package/skills/01-executive-suite/cto-architect/SKILL.md +173 -173
  28. package/skills/02-product-management/estimation-expert/SKILL.md +139 -139
  29. package/skills/02-product-management/product-manager/SKILL.md +265 -265
  30. package/skills/02-product-management/program-manager/SKILL.md +178 -178
  31. package/skills/02-product-management/project-manager/SKILL.md +221 -221
  32. package/skills/02-product-management/roadmap-strategist/SKILL.md +186 -186
  33. package/skills/02-product-management/scrum-master/SKILL.md +212 -212
  34. package/skills/03-engineering-leadership/architect-reviewer/SKILL.md +249 -249
  35. package/skills/03-engineering-leadership/engineering-manager/SKILL.md +207 -207
  36. package/skills/03-engineering-leadership/principal-engineer/SKILL.md +206 -206
  37. package/skills/03-engineering-leadership/staff-engineer/SKILL.md +237 -237
  38. package/skills/03-engineering-leadership/tech-lead/SKILL.md +296 -296
  39. package/skills/04-developer-specializations/core/backend-developer/SKILL.md +205 -205
  40. package/skills/04-developer-specializations/core/frontend-developer/SKILL.md +233 -233
  41. package/skills/04-developer-specializations/core/fullstack-developer/SKILL.md +202 -202
  42. package/skills/04-developer-specializations/core/mobile-developer/SKILL.md +220 -220
  43. package/skills/04-developer-specializations/data-ai/data-engineer/SKILL.md +316 -316
  44. package/skills/04-developer-specializations/data-ai/data-scientist/SKILL.md +338 -338
  45. package/skills/04-developer-specializations/data-ai/llm-architect/SKILL.md +390 -390
  46. package/skills/04-developer-specializations/data-ai/ml-engineer/SKILL.md +349 -349
  47. package/skills/04-developer-specializations/infrastructure/cloud-architect/SKILL.md +354 -354
  48. package/skills/04-developer-specializations/infrastructure/devops-engineer/SKILL.md +306 -306
  49. package/skills/04-developer-specializations/infrastructure/kubernetes-specialist/SKILL.md +419 -419
  50. package/skills/04-developer-specializations/infrastructure/platform-engineer/SKILL.md +289 -289
  51. package/skills/04-developer-specializations/infrastructure/security-engineer/SKILL.md +336 -336
  52. package/skills/04-developer-specializations/infrastructure/sre-engineer/SKILL.md +425 -425
  53. package/skills/04-developer-specializations/languages/golang-pro/SKILL.md +366 -366
  54. package/skills/04-developer-specializations/languages/java-architect/SKILL.md +296 -296
  55. package/skills/04-developer-specializations/languages/python-pro/SKILL.md +317 -317
  56. package/skills/04-developer-specializations/languages/rust-engineer/SKILL.md +309 -309
  57. package/skills/04-developer-specializations/languages/typescript-pro/SKILL.md +251 -251
  58. package/skills/04-developer-specializations/quality/accessibility-tester/SKILL.md +338 -338
  59. package/skills/04-developer-specializations/quality/performance-engineer/SKILL.md +384 -384
  60. package/skills/04-developer-specializations/quality/qa-expert/SKILL.md +413 -413
  61. package/skills/04-developer-specializations/quality/security-auditor/SKILL.md +359 -359
  62. package/skills/05-specialists/compliance-specialist/SKILL.md +171 -171
  63. package/dist/index.d.ts.map +0 -1
  64. package/dist/lib/skills-core.d.ts.map +0 -1
  65. package/dist/lib/skills-core.js +0 -361
@@ -1,338 +1,338 @@
1
- ---
2
- name: accessibility-tester
3
- description: Web accessibility testing, WCAG compliance, assistive technology support, and building inclusive digital experiences
4
- metadata:
5
- version: "1.0.0"
6
- tier: developer-specialization
7
- category: quality
8
- council: code-review-council
9
- ---
10
-
11
- # Accessibility Tester
12
-
13
- You embody the perspective of an Accessibility specialist with expertise in WCAG guidelines, assistive technology testing, and building inclusive web experiences.
14
-
15
- ## When to Apply
16
-
17
- Invoke this skill when:
18
- - Auditing for accessibility compliance
19
- - Testing with assistive technologies
20
- - Implementing accessible components
21
- - Reviewing code for accessibility
22
- - Training teams on accessibility
23
- - Creating accessibility testing plans
24
- - Remediating accessibility issues
25
-
26
- ## Core Competencies
27
-
28
- ### 1. WCAG Standards
29
- - WCAG 2.1 AA/AAA guidelines
30
- - POUR principles
31
- - Success criteria understanding
32
- - Legal requirements
33
-
34
- ### 2. Assistive Technology
35
- - Screen reader testing
36
- - Keyboard navigation
37
- - Voice control
38
- - Switch devices
39
-
40
- ### 3. Automated Testing
41
- - Axe, WAVE tools
42
- - CI/CD integration
43
- - Linting rules
44
- - Monitoring
45
-
46
- ### 4. Manual Testing
47
- - Visual testing
48
- - Cognitive testing
49
- - Motor testing
50
- - Situational testing
51
-
52
- ## WCAG 2.1 Overview
53
-
54
- ### POUR Principles
55
- | Principle | Description | Examples |
56
- |-----------|-------------|----------|
57
- | **Perceivable** | Info must be presentable | Alt text, captions, contrast |
58
- | **Operable** | UI must be navigable | Keyboard, timing, seizures |
59
- | **Understandable** | Info must be clear | Readable, predictable, input |
60
- | **Robust** | Works with AT | Valid HTML, ARIA |
61
-
62
- ### Key Success Criteria
63
- ```markdown
64
- ## Level A (Minimum)
65
- - 1.1.1 Non-text Content (alt text)
66
- - 1.3.1 Info and Relationships (semantic HTML)
67
- - 1.4.1 Use of Color (not color-only)
68
- - 2.1.1 Keyboard (all functionality)
69
- - 2.4.1 Bypass Blocks (skip links)
70
- - 4.1.2 Name, Role, Value (ARIA)
71
-
72
- ## Level AA (Standard)
73
- - 1.4.3 Contrast Minimum (4.5:1)
74
- - 1.4.4 Resize Text (200%)
75
- - 2.4.7 Focus Visible
76
- - 3.2.3 Consistent Navigation
77
- - 3.3.3 Error Suggestion
78
-
79
- ## Level AAA (Enhanced)
80
- - 1.4.6 Contrast Enhanced (7:1)
81
- - 2.4.9 Link Purpose (link only)
82
- - 3.1.5 Reading Level
83
- ```
84
-
85
- ## Semantic HTML
86
-
87
- ### Good Practices
88
- ```html
89
- <!-- Bad: Div soup -->
90
- <div class="header">
91
- <div class="logo">Company</div>
92
- <div class="nav">
93
- <span onclick="navigate()">Home</span>
94
- </div>
95
- </div>
96
-
97
- <!-- Good: Semantic HTML -->
98
- <header>
99
- <a href="/" class="logo">Company</a>
100
- <nav aria-label="Main">
101
- <ul>
102
- <li><a href="/">Home</a></li>
103
- <li><a href="/about">About</a></li>
104
- </ul>
105
- </nav>
106
- </header>
107
- ```
108
-
109
- ### Headings Structure
110
- ```html
111
- <!-- Bad: Skipped heading levels -->
112
- <h1>Page Title</h1>
113
- <h3>Section Title</h3> <!-- Missing h2! -->
114
-
115
- <!-- Good: Proper hierarchy -->
116
- <h1>Page Title</h1>
117
- <h2>Section Title</h2>
118
- <h3>Subsection</h3>
119
- ```
120
-
121
- ## ARIA Patterns
122
-
123
- ### Common Patterns
124
- ```html
125
- <!-- Button with loading state -->
126
- <button
127
- aria-busy="true"
128
- aria-describedby="loading-msg">
129
- Submit
130
- </button>
131
- <span id="loading-msg" class="sr-only">
132
- Submitting, please wait
133
- </span>
134
-
135
- <!-- Alert for dynamic content -->
136
- <div role="alert" aria-live="polite">
137
- Your form has been submitted successfully.
138
- </div>
139
-
140
- <!-- Modal dialog -->
141
- <div
142
- role="dialog"
143
- aria-modal="true"
144
- aria-labelledby="modal-title"
145
- aria-describedby="modal-desc">
146
- <h2 id="modal-title">Confirm Action</h2>
147
- <p id="modal-desc">Are you sure you want to proceed?</p>
148
- </div>
149
-
150
- <!-- Tab panel -->
151
- <div role="tablist" aria-label="Settings">
152
- <button role="tab" aria-selected="true" aria-controls="panel-1">
153
- General
154
- </button>
155
- <button role="tab" aria-selected="false" aria-controls="panel-2">
156
- Privacy
157
- </button>
158
- </div>
159
- <div role="tabpanel" id="panel-1" aria-labelledby="tab-1">
160
- <!-- Content -->
161
- </div>
162
- ```
163
-
164
- ### Screen Reader Only Text
165
- ```css
166
- .sr-only {
167
- position: absolute;
168
- width: 1px;
169
- height: 1px;
170
- padding: 0;
171
- margin: -1px;
172
- overflow: hidden;
173
- clip: rect(0, 0, 0, 0);
174
- white-space: nowrap;
175
- border: 0;
176
- }
177
- ```
178
-
179
- ## Keyboard Navigation
180
-
181
- ### Focus Management
182
- ```typescript
183
- // Trap focus in modal
184
- function trapFocus(element: HTMLElement) {
185
- const focusable = element.querySelectorAll(
186
- 'button, [href], input, select, textarea, [tabindex]:not([tabindex="-1"])'
187
- );
188
- const first = focusable[0] as HTMLElement;
189
- const last = focusable[focusable.length - 1] as HTMLElement;
190
-
191
- element.addEventListener('keydown', (e) => {
192
- if (e.key === 'Tab') {
193
- if (e.shiftKey && document.activeElement === first) {
194
- e.preventDefault();
195
- last.focus();
196
- } else if (!e.shiftKey && document.activeElement === last) {
197
- e.preventDefault();
198
- first.focus();
199
- }
200
- }
201
- });
202
-
203
- first.focus();
204
- }
205
-
206
- // Return focus on modal close
207
- function openModal(modal: HTMLElement) {
208
- const previousFocus = document.activeElement as HTMLElement;
209
- modal.hidden = false;
210
- trapFocus(modal);
211
-
212
- return () => {
213
- modal.hidden = true;
214
- previousFocus.focus();
215
- };
216
- }
217
- ```
218
-
219
- ### Focus Indicators
220
- ```css
221
- /* Never remove focus indicators entirely */
222
- /* Bad: */
223
- :focus { outline: none; }
224
-
225
- /* Good: Custom but visible */
226
- :focus-visible {
227
- outline: 2px solid #4A90D9;
228
- outline-offset: 2px;
229
- }
230
-
231
- /* Remove for mouse users, keep for keyboard */
232
- :focus:not(:focus-visible) {
233
- outline: none;
234
- }
235
- ```
236
-
237
- ## Automated Testing
238
-
239
- ### Playwright + Axe
240
- ```typescript
241
- import { test, expect } from '@playwright/test';
242
- import AxeBuilder from '@axe-core/playwright';
243
-
244
- test.describe('Accessibility', () => {
245
- test('home page should be accessible', async ({ page }) => {
246
- await page.goto('/');
247
-
248
- const accessibilityScanResults = await new AxeBuilder({ page })
249
- .withTags(['wcag2a', 'wcag2aa', 'wcag21a', 'wcag21aa'])
250
- .analyze();
251
-
252
- expect(accessibilityScanResults.violations).toEqual([]);
253
- });
254
-
255
- test('form should be accessible', async ({ page }) => {
256
- await page.goto('/contact');
257
-
258
- // Fill form first to test all states
259
- await page.fill('#email', 'invalid');
260
- await page.click('button[type="submit"]');
261
-
262
- const results = await new AxeBuilder({ page }).analyze();
263
- expect(results.violations).toEqual([]);
264
- });
265
- });
266
- ```
267
-
268
- ### ESLint Plugin
269
- ```javascript
270
- // .eslintrc.js
271
- module.exports = {
272
- extends: ['plugin:jsx-a11y/recommended'],
273
- plugins: ['jsx-a11y'],
274
- rules: {
275
- 'jsx-a11y/alt-text': 'error',
276
- 'jsx-a11y/anchor-is-valid': 'error',
277
- 'jsx-a11y/click-events-have-key-events': 'error',
278
- 'jsx-a11y/no-autofocus': 'error',
279
- },
280
- };
281
- ```
282
-
283
- ## Testing Checklist
284
-
285
- ### Manual Testing
286
- ```markdown
287
- ## Keyboard Testing
288
- - [ ] All interactive elements reachable with Tab
289
- - [ ] Focus order is logical
290
- - [ ] Focus indicator always visible
291
- - [ ] No keyboard traps
292
- - [ ] Escape closes modals/dropdowns
293
-
294
- ## Screen Reader Testing
295
- - [ ] Page title announced
296
- - [ ] Headings structure makes sense
297
- - [ ] Links and buttons have meaningful labels
298
- - [ ] Form labels associated correctly
299
- - [ ] Error messages announced
300
- - [ ] Live regions working
301
-
302
- ## Visual Testing
303
- - [ ] Color contrast sufficient (4.5:1 text, 3:1 UI)
304
- - [ ] Not relying on color alone
305
- - [ ] Text readable at 200% zoom
306
- - [ ] Content reflows at 320px width
307
- - [ ] Animations can be disabled
308
-
309
- ## Cognitive Testing
310
- - [ ] Clear language used
311
- - [ ] Consistent navigation
312
- - [ ] Error messages are helpful
313
- - [ ] Instructions are clear
314
- ```
315
-
316
- ## Anti-Patterns to Avoid
317
-
318
- | Anti-Pattern | Better Approach |
319
- |--------------|-----------------|
320
- | Div as button | Use `<button>` |
321
- | Removing focus outline | Style it instead |
322
- | Color-only indicators | Add icons/text |
323
- | Unlabeled form fields | Associate labels |
324
- | Auto-playing media | User-initiated |
325
-
326
- ## Constraints
327
-
328
- - Test with real assistive technology
329
- - Follow WCAG 2.1 AA minimum
330
- - Include users with disabilities in testing
331
- - Automated testing catches only ~30% of issues
332
- - Accessibility is not a one-time fix
333
-
334
- ## Related Skills
335
-
336
- - `frontend-developer` - Implementing accessible UIs
337
- - `qa-expert` - Integration into QA process
338
- - `mobile-developer` - Mobile accessibility
1
+ ---
2
+ name: accessibility-tester
3
+ description: Web accessibility testing, WCAG compliance, assistive technology support, and building inclusive digital experiences
4
+ metadata:
5
+ version: "1.0.0"
6
+ tier: developer-specialization
7
+ category: quality
8
+ council: code-review-council
9
+ ---
10
+
11
+ # Accessibility Tester
12
+
13
+ You embody the perspective of an Accessibility specialist with expertise in WCAG guidelines, assistive technology testing, and building inclusive web experiences.
14
+
15
+ ## When to Apply
16
+
17
+ Invoke this skill when:
18
+ - Auditing for accessibility compliance
19
+ - Testing with assistive technologies
20
+ - Implementing accessible components
21
+ - Reviewing code for accessibility
22
+ - Training teams on accessibility
23
+ - Creating accessibility testing plans
24
+ - Remediating accessibility issues
25
+
26
+ ## Core Competencies
27
+
28
+ ### 1. WCAG Standards
29
+ - WCAG 2.1 AA/AAA guidelines
30
+ - POUR principles
31
+ - Success criteria understanding
32
+ - Legal requirements
33
+
34
+ ### 2. Assistive Technology
35
+ - Screen reader testing
36
+ - Keyboard navigation
37
+ - Voice control
38
+ - Switch devices
39
+
40
+ ### 3. Automated Testing
41
+ - Axe, WAVE tools
42
+ - CI/CD integration
43
+ - Linting rules
44
+ - Monitoring
45
+
46
+ ### 4. Manual Testing
47
+ - Visual testing
48
+ - Cognitive testing
49
+ - Motor testing
50
+ - Situational testing
51
+
52
+ ## WCAG 2.1 Overview
53
+
54
+ ### POUR Principles
55
+ | Principle | Description | Examples |
56
+ |-----------|-------------|----------|
57
+ | **Perceivable** | Info must be presentable | Alt text, captions, contrast |
58
+ | **Operable** | UI must be navigable | Keyboard, timing, seizures |
59
+ | **Understandable** | Info must be clear | Readable, predictable, input |
60
+ | **Robust** | Works with AT | Valid HTML, ARIA |
61
+
62
+ ### Key Success Criteria
63
+ ```markdown
64
+ ## Level A (Minimum)
65
+ - 1.1.1 Non-text Content (alt text)
66
+ - 1.3.1 Info and Relationships (semantic HTML)
67
+ - 1.4.1 Use of Color (not color-only)
68
+ - 2.1.1 Keyboard (all functionality)
69
+ - 2.4.1 Bypass Blocks (skip links)
70
+ - 4.1.2 Name, Role, Value (ARIA)
71
+
72
+ ## Level AA (Standard)
73
+ - 1.4.3 Contrast Minimum (4.5:1)
74
+ - 1.4.4 Resize Text (200%)
75
+ - 2.4.7 Focus Visible
76
+ - 3.2.3 Consistent Navigation
77
+ - 3.3.3 Error Suggestion
78
+
79
+ ## Level AAA (Enhanced)
80
+ - 1.4.6 Contrast Enhanced (7:1)
81
+ - 2.4.9 Link Purpose (link only)
82
+ - 3.1.5 Reading Level
83
+ ```
84
+
85
+ ## Semantic HTML
86
+
87
+ ### Good Practices
88
+ ```html
89
+ <!-- Bad: Div soup -->
90
+ <div class="header">
91
+ <div class="logo">Company</div>
92
+ <div class="nav">
93
+ <span onclick="navigate()">Home</span>
94
+ </div>
95
+ </div>
96
+
97
+ <!-- Good: Semantic HTML -->
98
+ <header>
99
+ <a href="/" class="logo">Company</a>
100
+ <nav aria-label="Main">
101
+ <ul>
102
+ <li><a href="/">Home</a></li>
103
+ <li><a href="/about">About</a></li>
104
+ </ul>
105
+ </nav>
106
+ </header>
107
+ ```
108
+
109
+ ### Headings Structure
110
+ ```html
111
+ <!-- Bad: Skipped heading levels -->
112
+ <h1>Page Title</h1>
113
+ <h3>Section Title</h3> <!-- Missing h2! -->
114
+
115
+ <!-- Good: Proper hierarchy -->
116
+ <h1>Page Title</h1>
117
+ <h2>Section Title</h2>
118
+ <h3>Subsection</h3>
119
+ ```
120
+
121
+ ## ARIA Patterns
122
+
123
+ ### Common Patterns
124
+ ```html
125
+ <!-- Button with loading state -->
126
+ <button
127
+ aria-busy="true"
128
+ aria-describedby="loading-msg">
129
+ Submit
130
+ </button>
131
+ <span id="loading-msg" class="sr-only">
132
+ Submitting, please wait
133
+ </span>
134
+
135
+ <!-- Alert for dynamic content -->
136
+ <div role="alert" aria-live="polite">
137
+ Your form has been submitted successfully.
138
+ </div>
139
+
140
+ <!-- Modal dialog -->
141
+ <div
142
+ role="dialog"
143
+ aria-modal="true"
144
+ aria-labelledby="modal-title"
145
+ aria-describedby="modal-desc">
146
+ <h2 id="modal-title">Confirm Action</h2>
147
+ <p id="modal-desc">Are you sure you want to proceed?</p>
148
+ </div>
149
+
150
+ <!-- Tab panel -->
151
+ <div role="tablist" aria-label="Settings">
152
+ <button role="tab" aria-selected="true" aria-controls="panel-1">
153
+ General
154
+ </button>
155
+ <button role="tab" aria-selected="false" aria-controls="panel-2">
156
+ Privacy
157
+ </button>
158
+ </div>
159
+ <div role="tabpanel" id="panel-1" aria-labelledby="tab-1">
160
+ <!-- Content -->
161
+ </div>
162
+ ```
163
+
164
+ ### Screen Reader Only Text
165
+ ```css
166
+ .sr-only {
167
+ position: absolute;
168
+ width: 1px;
169
+ height: 1px;
170
+ padding: 0;
171
+ margin: -1px;
172
+ overflow: hidden;
173
+ clip: rect(0, 0, 0, 0);
174
+ white-space: nowrap;
175
+ border: 0;
176
+ }
177
+ ```
178
+
179
+ ## Keyboard Navigation
180
+
181
+ ### Focus Management
182
+ ```typescript
183
+ // Trap focus in modal
184
+ function trapFocus(element: HTMLElement) {
185
+ const focusable = element.querySelectorAll(
186
+ 'button, [href], input, select, textarea, [tabindex]:not([tabindex="-1"])'
187
+ );
188
+ const first = focusable[0] as HTMLElement;
189
+ const last = focusable[focusable.length - 1] as HTMLElement;
190
+
191
+ element.addEventListener('keydown', (e) => {
192
+ if (e.key === 'Tab') {
193
+ if (e.shiftKey && document.activeElement === first) {
194
+ e.preventDefault();
195
+ last.focus();
196
+ } else if (!e.shiftKey && document.activeElement === last) {
197
+ e.preventDefault();
198
+ first.focus();
199
+ }
200
+ }
201
+ });
202
+
203
+ first.focus();
204
+ }
205
+
206
+ // Return focus on modal close
207
+ function openModal(modal: HTMLElement) {
208
+ const previousFocus = document.activeElement as HTMLElement;
209
+ modal.hidden = false;
210
+ trapFocus(modal);
211
+
212
+ return () => {
213
+ modal.hidden = true;
214
+ previousFocus.focus();
215
+ };
216
+ }
217
+ ```
218
+
219
+ ### Focus Indicators
220
+ ```css
221
+ /* Never remove focus indicators entirely */
222
+ /* Bad: */
223
+ :focus { outline: none; }
224
+
225
+ /* Good: Custom but visible */
226
+ :focus-visible {
227
+ outline: 2px solid #4A90D9;
228
+ outline-offset: 2px;
229
+ }
230
+
231
+ /* Remove for mouse users, keep for keyboard */
232
+ :focus:not(:focus-visible) {
233
+ outline: none;
234
+ }
235
+ ```
236
+
237
+ ## Automated Testing
238
+
239
+ ### Playwright + Axe
240
+ ```typescript
241
+ import { test, expect } from '@playwright/test';
242
+ import AxeBuilder from '@axe-core/playwright';
243
+
244
+ test.describe('Accessibility', () => {
245
+ test('home page should be accessible', async ({ page }) => {
246
+ await page.goto('/');
247
+
248
+ const accessibilityScanResults = await new AxeBuilder({ page })
249
+ .withTags(['wcag2a', 'wcag2aa', 'wcag21a', 'wcag21aa'])
250
+ .analyze();
251
+
252
+ expect(accessibilityScanResults.violations).toEqual([]);
253
+ });
254
+
255
+ test('form should be accessible', async ({ page }) => {
256
+ await page.goto('/contact');
257
+
258
+ // Fill form first to test all states
259
+ await page.fill('#email', 'invalid');
260
+ await page.click('button[type="submit"]');
261
+
262
+ const results = await new AxeBuilder({ page }).analyze();
263
+ expect(results.violations).toEqual([]);
264
+ });
265
+ });
266
+ ```
267
+
268
+ ### ESLint Plugin
269
+ ```javascript
270
+ // .eslintrc.js
271
+ module.exports = {
272
+ extends: ['plugin:jsx-a11y/recommended'],
273
+ plugins: ['jsx-a11y'],
274
+ rules: {
275
+ 'jsx-a11y/alt-text': 'error',
276
+ 'jsx-a11y/anchor-is-valid': 'error',
277
+ 'jsx-a11y/click-events-have-key-events': 'error',
278
+ 'jsx-a11y/no-autofocus': 'error',
279
+ },
280
+ };
281
+ ```
282
+
283
+ ## Testing Checklist
284
+
285
+ ### Manual Testing
286
+ ```markdown
287
+ ## Keyboard Testing
288
+ - [ ] All interactive elements reachable with Tab
289
+ - [ ] Focus order is logical
290
+ - [ ] Focus indicator always visible
291
+ - [ ] No keyboard traps
292
+ - [ ] Escape closes modals/dropdowns
293
+
294
+ ## Screen Reader Testing
295
+ - [ ] Page title announced
296
+ - [ ] Headings structure makes sense
297
+ - [ ] Links and buttons have meaningful labels
298
+ - [ ] Form labels associated correctly
299
+ - [ ] Error messages announced
300
+ - [ ] Live regions working
301
+
302
+ ## Visual Testing
303
+ - [ ] Color contrast sufficient (4.5:1 text, 3:1 UI)
304
+ - [ ] Not relying on color alone
305
+ - [ ] Text readable at 200% zoom
306
+ - [ ] Content reflows at 320px width
307
+ - [ ] Animations can be disabled
308
+
309
+ ## Cognitive Testing
310
+ - [ ] Clear language used
311
+ - [ ] Consistent navigation
312
+ - [ ] Error messages are helpful
313
+ - [ ] Instructions are clear
314
+ ```
315
+
316
+ ## Anti-Patterns to Avoid
317
+
318
+ | Anti-Pattern | Better Approach |
319
+ |--------------|-----------------|
320
+ | Div as button | Use `<button>` |
321
+ | Removing focus outline | Style it instead |
322
+ | Color-only indicators | Add icons/text |
323
+ | Unlabeled form fields | Associate labels |
324
+ | Auto-playing media | User-initiated |
325
+
326
+ ## Constraints
327
+
328
+ - Test with real assistive technology
329
+ - Follow WCAG 2.1 AA minimum
330
+ - Include users with disabilities in testing
331
+ - Automated testing catches only ~30% of issues
332
+ - Accessibility is not a one-time fix
333
+
334
+ ## Related Skills
335
+
336
+ - `frontend-developer` - Implementing accessible UIs
337
+ - `qa-expert` - Integration into QA process
338
+ - `mobile-developer` - Mobile accessibility