@accesslint/storybook-addon 0.8.3 → 0.8.4
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.
- package/README.md +8 -5
- package/dist/manager.js +58 -20
- package/dist/portable.cjs +21 -8
- package/dist/portable.d.cts +2 -1
- package/dist/portable.d.ts +2 -1
- package/dist/portable.js +21 -8
- package/dist/preview.cjs +21 -8
- package/dist/preview.d.cts +2 -1
- package/dist/preview.d.ts +2 -1
- package/dist/preview.js +21 -8
- package/dist/vitest-plugin.d.cts +1 -1
- package/dist/vitest-plugin.d.ts +1 -1
- package/dist/vitest-setup.cjs +20 -8
- package/dist/vitest-setup.js +21 -9
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -5,7 +5,8 @@
|
|
|
5
5
|
|
|
6
6
|
Catch accessibility violations in your Storybook stories as you develop. Powered by [@accesslint/core](https://accesslint.com/core).
|
|
7
7
|
|
|
8
|
-
<img
|
|
8
|
+
<img height="414" alt="Storybook screenshot with alt text violation in the details of the AccessLint tab" src="https://github.com/user-attachments/assets/42bb12ee-3a07-4443-8b60-35c2c9c735a9" />
|
|
9
|
+
|
|
9
10
|
|
|
10
11
|
## Getting Started
|
|
11
12
|
|
|
@@ -25,6 +26,8 @@ export default config;
|
|
|
25
26
|
|
|
26
27
|
Restart Storybook and an **AccessLint** panel will appear in the addon bar. Every story is audited automatically after it renders.
|
|
27
28
|
|
|
29
|
+
Expand any violation to see the failing element, WCAG criteria, and remediation guidance. Click **Highlight** to outline the element in the preview.
|
|
30
|
+
|
|
28
31
|
## Vitest integration
|
|
29
32
|
|
|
30
33
|
If you use [`@storybook/addon-vitest`](https://storybook.js.org/docs/writing-tests/vitest-plugin), add the AccessLint plugin next to `storybookTest()` in your Vite config:
|
|
@@ -187,18 +190,18 @@ configureRules({
|
|
|
187
190
|
|
|
188
191
|
### Skipping stories with tags
|
|
189
192
|
|
|
190
|
-
Tag individual stories or entire components with `"
|
|
193
|
+
Tag individual stories or entire components with `"skip-accesslint"` to skip auditing:
|
|
191
194
|
|
|
192
195
|
```ts
|
|
193
196
|
// Skip a single story
|
|
194
197
|
export const Prototype = {
|
|
195
|
-
tags: ["
|
|
198
|
+
tags: ["skip-accesslint"],
|
|
196
199
|
};
|
|
197
200
|
|
|
198
201
|
// Skip all stories for a component
|
|
199
202
|
export default {
|
|
200
203
|
component: ExperimentalWidget,
|
|
201
|
-
tags: ["
|
|
204
|
+
tags: ["skip-accesslint"],
|
|
202
205
|
};
|
|
203
206
|
```
|
|
204
207
|
|
|
@@ -206,7 +209,7 @@ With the Vitest plugin, you can also define custom skip tags:
|
|
|
206
209
|
|
|
207
210
|
```ts
|
|
208
211
|
accesslintTest({
|
|
209
|
-
tags: { skip: ["
|
|
212
|
+
tags: { skip: ["skip-accesslint", "wip"] },
|
|
210
213
|
});
|
|
211
214
|
```
|
|
212
215
|
|
package/dist/manager.js
CHANGED
|
@@ -2,7 +2,7 @@ import React, { useMemo, useState, useRef, useCallback } from 'react';
|
|
|
2
2
|
import * as managerApi from 'storybook/internal/manager-api';
|
|
3
3
|
import { useChannel } from 'storybook/internal/manager-api';
|
|
4
4
|
import { styled, useTheme } from 'storybook/internal/theming';
|
|
5
|
-
import { STORY_CHANGED
|
|
5
|
+
import { STORY_CHANGED } from 'storybook/internal/core-events';
|
|
6
6
|
|
|
7
7
|
var __require = /* @__PURE__ */ ((x) => typeof require !== "undefined" ? require : typeof Proxy !== "undefined" ? new Proxy(x, {
|
|
8
8
|
get: (a, b) => (typeof require !== "undefined" ? require : a)[b]
|
|
@@ -15,6 +15,10 @@ var __require = /* @__PURE__ */ ((x) => typeof require !== "undefined" ? require
|
|
|
15
15
|
var ADDON_ID = "accesslint/a11y";
|
|
16
16
|
var PARAM_KEY = "accesslint";
|
|
17
17
|
var STATUS_TYPE_ID = "accesslint/a11y";
|
|
18
|
+
var RESULT_EVENT = `${ADDON_ID}/result`;
|
|
19
|
+
var HIGHLIGHT_ADDON_ID = "storybook/highlight";
|
|
20
|
+
var HIGHLIGHT = `${HIGHLIGHT_ADDON_ID}/add`;
|
|
21
|
+
var REMOVE_HIGHLIGHT = `${HIGHLIGHT_ADDON_ID}/remove`;
|
|
18
22
|
var IMPACT_COLOR = {
|
|
19
23
|
critical: "#d32f2f",
|
|
20
24
|
serious: "#d32f2f",
|
|
@@ -58,29 +62,30 @@ var Panel = ({ active }) => {
|
|
|
58
62
|
const [ruleCount, setRuleCount] = useState(0);
|
|
59
63
|
const [skippedReason, setSkippedReason] = useState(null);
|
|
60
64
|
const [expandedIndex, setExpandedIndex] = useState(null);
|
|
65
|
+
const [highlightedIndex, setHighlightedIndex] = useState(null);
|
|
61
66
|
const buttonRefs = useRef([]);
|
|
62
|
-
useChannel({
|
|
63
|
-
[
|
|
64
|
-
const report = reporters.find((r) => r.type === "accesslint");
|
|
65
|
-
if (!report) return;
|
|
66
|
-
const result = report.result;
|
|
67
|
+
const emit = useChannel({
|
|
68
|
+
[RESULT_EVENT]: ({ result }) => {
|
|
67
69
|
if (result.skipped) {
|
|
68
70
|
setViolations([]);
|
|
69
71
|
setRuleCount(0);
|
|
70
72
|
setSkippedReason(result.reason ?? "skipped");
|
|
71
73
|
setExpandedIndex(null);
|
|
74
|
+
setHighlightedIndex(null);
|
|
72
75
|
return;
|
|
73
76
|
}
|
|
74
77
|
setViolations(result.violations ?? []);
|
|
75
78
|
setRuleCount(result.ruleCount ?? 0);
|
|
76
79
|
setSkippedReason(null);
|
|
77
80
|
setExpandedIndex(null);
|
|
81
|
+
setHighlightedIndex(null);
|
|
78
82
|
},
|
|
79
83
|
[STORY_CHANGED]: () => {
|
|
80
84
|
setViolations([]);
|
|
81
85
|
setRuleCount(0);
|
|
82
86
|
setSkippedReason(null);
|
|
83
87
|
setExpandedIndex(null);
|
|
88
|
+
setHighlightedIndex(null);
|
|
84
89
|
}
|
|
85
90
|
});
|
|
86
91
|
const sorted = useMemo(
|
|
@@ -133,7 +138,13 @@ var Panel = ({ active }) => {
|
|
|
133
138
|
buttonRefs.current[i] = el;
|
|
134
139
|
},
|
|
135
140
|
type: "button",
|
|
136
|
-
onClick: () =>
|
|
141
|
+
onClick: () => {
|
|
142
|
+
setExpandedIndex(isOpen ? null : i);
|
|
143
|
+
if (highlightedIndex !== null) {
|
|
144
|
+
emit(REMOVE_HIGHLIGHT);
|
|
145
|
+
setHighlightedIndex(null);
|
|
146
|
+
}
|
|
147
|
+
},
|
|
137
148
|
onKeyDown: (e) => handleKeyDown(e, i),
|
|
138
149
|
"aria-expanded": isOpen,
|
|
139
150
|
style: {
|
|
@@ -186,7 +197,38 @@ var Panel = ({ active }) => {
|
|
|
186
197
|
}
|
|
187
198
|
},
|
|
188
199
|
ref
|
|
189
|
-
))), v.guidance && /* @__PURE__ */ React.createElement("div", { style: { marginBottom: "8px" } }, /* @__PURE__ */ React.createElement("div", { style: { fontSize: "11px", fontWeight: 500, color: colors.textMuted, marginBottom: "4px" } }, "How to fix"), /* @__PURE__ */ React.createElement("p", { style: { margin: 0, fontSize: "12px", color: colors.text, whiteSpace: "pre-wrap" } }, v.guidance)), v.html && /* @__PURE__ */ React.createElement("div", { style: { marginBottom: "8px" } }, /* @__PURE__ */ React.createElement("div", { style: {
|
|
200
|
+
))), v.guidance && /* @__PURE__ */ React.createElement("div", { style: { marginBottom: "8px" } }, /* @__PURE__ */ React.createElement("div", { style: { fontSize: "11px", fontWeight: 500, color: colors.textMuted, marginBottom: "4px" } }, "How to fix"), /* @__PURE__ */ React.createElement("p", { style: { margin: 0, fontSize: "12px", color: colors.text, whiteSpace: "pre-wrap" } }, v.guidance)), v.html && /* @__PURE__ */ React.createElement("div", { style: { marginBottom: "8px" } }, /* @__PURE__ */ React.createElement("div", { style: { display: "flex", alignItems: "center", justifyContent: "space-between", marginBottom: "4px" } }, /* @__PURE__ */ React.createElement("div", { style: { fontSize: "11px", fontWeight: 500, color: colors.textMuted } }, "Element"), /* @__PURE__ */ React.createElement(
|
|
201
|
+
"button",
|
|
202
|
+
{
|
|
203
|
+
type: "button",
|
|
204
|
+
onClick: () => {
|
|
205
|
+
if (highlightedIndex === i) {
|
|
206
|
+
emit(REMOVE_HIGHLIGHT);
|
|
207
|
+
setHighlightedIndex(null);
|
|
208
|
+
} else {
|
|
209
|
+
const color = v.impact === "critical" || v.impact === "serious" ? "#d32f2f" : "#c43e00";
|
|
210
|
+
const localSelector = v.selector.replace(/^.*>>>\s*iframe>\s*/, "");
|
|
211
|
+
emit(HIGHLIGHT, {
|
|
212
|
+
elements: [localSelector],
|
|
213
|
+
color,
|
|
214
|
+
style: "solid"
|
|
215
|
+
});
|
|
216
|
+
setHighlightedIndex(i);
|
|
217
|
+
}
|
|
218
|
+
},
|
|
219
|
+
style: {
|
|
220
|
+
padding: "2px 8px",
|
|
221
|
+
fontSize: "11px",
|
|
222
|
+
fontWeight: 500,
|
|
223
|
+
border: `1px solid ${colors.codeBorder}`,
|
|
224
|
+
borderRadius: "4px",
|
|
225
|
+
background: highlightedIndex === i ? IMPACT_COLOR[v.impact] : colors.codeBg,
|
|
226
|
+
color: highlightedIndex === i ? "#fff" : colors.text,
|
|
227
|
+
cursor: "pointer"
|
|
228
|
+
}
|
|
229
|
+
},
|
|
230
|
+
"Highlight"
|
|
231
|
+
)), /* @__PURE__ */ React.createElement(
|
|
190
232
|
"pre",
|
|
191
233
|
{
|
|
192
234
|
style: {
|
|
@@ -234,10 +276,8 @@ try {
|
|
|
234
276
|
var Title = () => {
|
|
235
277
|
const [count, setCount] = React.useState(0);
|
|
236
278
|
useChannel2({
|
|
237
|
-
[
|
|
238
|
-
|
|
239
|
-
const violations = report?.result?.violations;
|
|
240
|
-
setCount(violations?.length ?? 0);
|
|
279
|
+
[RESULT_EVENT]: ({ result }) => {
|
|
280
|
+
setCount(result.skipped ? 0 : result.violations?.length ?? 0);
|
|
241
281
|
}
|
|
242
282
|
});
|
|
243
283
|
return /* @__PURE__ */ React.createElement(React.Fragment, null, "AccessLint", count > 0 && /* @__PURE__ */ React.createElement("span", { style: {
|
|
@@ -286,20 +326,18 @@ var TestProviderWidget = () => {
|
|
|
286
326
|
return unsub;
|
|
287
327
|
}, [api]);
|
|
288
328
|
useChannel2({
|
|
289
|
-
[
|
|
290
|
-
const
|
|
291
|
-
if (!report) return;
|
|
292
|
-
const violations = report.result?.violations ?? [];
|
|
329
|
+
[RESULT_EVENT]: ({ storyId, result, status: status2 }) => {
|
|
330
|
+
const violations = result.skipped ? [] : result.violations ?? [];
|
|
293
331
|
setViolationCount(violations.length);
|
|
294
|
-
if (statusStore) {
|
|
332
|
+
if (statusStore && storyId) {
|
|
295
333
|
const hasViolations2 = violations.length > 0;
|
|
296
|
-
const isWarning =
|
|
334
|
+
const isWarning = status2 === "warning";
|
|
297
335
|
statusStore.set([{
|
|
298
|
-
value: hasViolations2 ? isWarning ? "status-value:warning" : "status-value:error" : "status-value:success",
|
|
336
|
+
value: result.skipped ? "status-value:unknown" : hasViolations2 ? isWarning ? "status-value:warning" : "status-value:error" : "status-value:success",
|
|
299
337
|
typeId: STATUS_TYPE_ID,
|
|
300
338
|
storyId,
|
|
301
339
|
title: "AccessLint",
|
|
302
|
-
description: hasViolations2 ? `${violations.length} violation${violations.length === 1 ? "" : "s"}` : "No violations",
|
|
340
|
+
description: result.skipped ? "Skipped" : hasViolations2 ? `${violations.length} violation${violations.length === 1 ? "" : "s"}` : "No violations",
|
|
303
341
|
sidebarContextMenu: true
|
|
304
342
|
}]);
|
|
305
343
|
}
|
package/dist/portable.cjs
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
3
|
var core = require('@accesslint/core');
|
|
4
|
+
var previewApi = require('storybook/preview-api');
|
|
4
5
|
|
|
5
6
|
var __defProp = Object.defineProperty;
|
|
6
7
|
var __export = (target, all) => {
|
|
@@ -13,6 +14,12 @@ var preview_exports = {};
|
|
|
13
14
|
__export(preview_exports, {
|
|
14
15
|
afterEach: () => afterEach
|
|
15
16
|
});
|
|
17
|
+
|
|
18
|
+
// src/constants.ts
|
|
19
|
+
var ADDON_ID = "accesslint/a11y";
|
|
20
|
+
var RESULT_EVENT = `${ADDON_ID}/result`;
|
|
21
|
+
|
|
22
|
+
// src/preview.ts
|
|
16
23
|
core.configureRules({
|
|
17
24
|
disabledRules: ["accesslint-045"]
|
|
18
25
|
});
|
|
@@ -51,19 +58,22 @@ var afterEach = async ({
|
|
|
51
58
|
reporting,
|
|
52
59
|
parameters,
|
|
53
60
|
viewMode,
|
|
54
|
-
tags
|
|
61
|
+
tags,
|
|
62
|
+
id
|
|
55
63
|
}) => {
|
|
56
64
|
const accesslintParam = parameters?.accesslint;
|
|
57
65
|
if (accesslintParam?.disable === true || accesslintParam?.test === "off") return;
|
|
58
66
|
if (viewMode !== "story") return;
|
|
59
67
|
const skipTags = typeof __ACCESSLINT_SKIP_TAGS__ !== "undefined" ? __ACCESSLINT_SKIP_TAGS__ : [];
|
|
60
|
-
const allSkipTags = ["
|
|
68
|
+
const allSkipTags = ["skip-accesslint", ...skipTags];
|
|
61
69
|
const matchedTag = tags?.find((t) => allSkipTags.includes(t));
|
|
62
70
|
if (matchedTag) {
|
|
71
|
+
const result2 = { skipped: true, reason: matchedTag };
|
|
72
|
+
previewApi.addons.getChannel().emit(RESULT_EVENT, { storyId: id, result: result2 });
|
|
63
73
|
reporting.addReport({
|
|
64
74
|
type: "accesslint",
|
|
65
75
|
version: 1,
|
|
66
|
-
result:
|
|
76
|
+
result: result2,
|
|
67
77
|
status: "passed"
|
|
68
78
|
});
|
|
69
79
|
return;
|
|
@@ -77,14 +87,17 @@ var afterEach = async ({
|
|
|
77
87
|
const enriched = enrichViolations(scoped);
|
|
78
88
|
const hasViolations = enriched.length > 0;
|
|
79
89
|
const mode = accesslintParam?.test === "todo" ? "warning" : "failed";
|
|
90
|
+
const status = hasViolations ? mode : "passed";
|
|
91
|
+
const result = {
|
|
92
|
+
violations: enriched,
|
|
93
|
+
ruleCount: core.getActiveRules().length
|
|
94
|
+
};
|
|
95
|
+
previewApi.addons.getChannel().emit(RESULT_EVENT, { storyId: id, result, status });
|
|
80
96
|
reporting.addReport({
|
|
81
97
|
type: "accesslint",
|
|
82
98
|
version: 1,
|
|
83
|
-
result
|
|
84
|
-
|
|
85
|
-
ruleCount: core.getActiveRules().length
|
|
86
|
-
},
|
|
87
|
-
status: hasViolations ? mode : "passed"
|
|
99
|
+
result,
|
|
100
|
+
status
|
|
88
101
|
});
|
|
89
102
|
};
|
|
90
103
|
|
package/dist/portable.d.cts
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
|
-
declare const afterEach: ({ reporting, parameters, viewMode, tags, }: {
|
|
1
|
+
declare const afterEach: ({ reporting, parameters, viewMode, tags, id, }: {
|
|
2
2
|
reporting: {
|
|
3
3
|
addReport: (report: Record<string, unknown>) => void;
|
|
4
4
|
};
|
|
5
5
|
parameters: Record<string, unknown>;
|
|
6
6
|
viewMode: string;
|
|
7
7
|
tags?: string[];
|
|
8
|
+
id?: string;
|
|
8
9
|
}) => Promise<void>;
|
|
9
10
|
|
|
10
11
|
declare const accesslintAnnotations_afterEach: typeof afterEach;
|
package/dist/portable.d.ts
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
|
-
declare const afterEach: ({ reporting, parameters, viewMode, tags, }: {
|
|
1
|
+
declare const afterEach: ({ reporting, parameters, viewMode, tags, id, }: {
|
|
2
2
|
reporting: {
|
|
3
3
|
addReport: (report: Record<string, unknown>) => void;
|
|
4
4
|
};
|
|
5
5
|
parameters: Record<string, unknown>;
|
|
6
6
|
viewMode: string;
|
|
7
7
|
tags?: string[];
|
|
8
|
+
id?: string;
|
|
8
9
|
}) => Promise<void>;
|
|
9
10
|
|
|
10
11
|
declare const accesslintAnnotations_afterEach: typeof afterEach;
|
package/dist/portable.js
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { configureRules, createChunkedAudit, getActiveRules, getRuleById } from '@accesslint/core';
|
|
2
|
+
import { addons } from 'storybook/preview-api';
|
|
2
3
|
|
|
3
4
|
var __defProp = Object.defineProperty;
|
|
4
5
|
var __export = (target, all) => {
|
|
@@ -11,6 +12,12 @@ var preview_exports = {};
|
|
|
11
12
|
__export(preview_exports, {
|
|
12
13
|
afterEach: () => afterEach
|
|
13
14
|
});
|
|
15
|
+
|
|
16
|
+
// src/constants.ts
|
|
17
|
+
var ADDON_ID = "accesslint/a11y";
|
|
18
|
+
var RESULT_EVENT = `${ADDON_ID}/result`;
|
|
19
|
+
|
|
20
|
+
// src/preview.ts
|
|
14
21
|
configureRules({
|
|
15
22
|
disabledRules: ["accesslint-045"]
|
|
16
23
|
});
|
|
@@ -49,19 +56,22 @@ var afterEach = async ({
|
|
|
49
56
|
reporting,
|
|
50
57
|
parameters,
|
|
51
58
|
viewMode,
|
|
52
|
-
tags
|
|
59
|
+
tags,
|
|
60
|
+
id
|
|
53
61
|
}) => {
|
|
54
62
|
const accesslintParam = parameters?.accesslint;
|
|
55
63
|
if (accesslintParam?.disable === true || accesslintParam?.test === "off") return;
|
|
56
64
|
if (viewMode !== "story") return;
|
|
57
65
|
const skipTags = typeof __ACCESSLINT_SKIP_TAGS__ !== "undefined" ? __ACCESSLINT_SKIP_TAGS__ : [];
|
|
58
|
-
const allSkipTags = ["
|
|
66
|
+
const allSkipTags = ["skip-accesslint", ...skipTags];
|
|
59
67
|
const matchedTag = tags?.find((t) => allSkipTags.includes(t));
|
|
60
68
|
if (matchedTag) {
|
|
69
|
+
const result2 = { skipped: true, reason: matchedTag };
|
|
70
|
+
addons.getChannel().emit(RESULT_EVENT, { storyId: id, result: result2 });
|
|
61
71
|
reporting.addReport({
|
|
62
72
|
type: "accesslint",
|
|
63
73
|
version: 1,
|
|
64
|
-
result:
|
|
74
|
+
result: result2,
|
|
65
75
|
status: "passed"
|
|
66
76
|
});
|
|
67
77
|
return;
|
|
@@ -75,14 +85,17 @@ var afterEach = async ({
|
|
|
75
85
|
const enriched = enrichViolations(scoped);
|
|
76
86
|
const hasViolations = enriched.length > 0;
|
|
77
87
|
const mode = accesslintParam?.test === "todo" ? "warning" : "failed";
|
|
88
|
+
const status = hasViolations ? mode : "passed";
|
|
89
|
+
const result = {
|
|
90
|
+
violations: enriched,
|
|
91
|
+
ruleCount: getActiveRules().length
|
|
92
|
+
};
|
|
93
|
+
addons.getChannel().emit(RESULT_EVENT, { storyId: id, result, status });
|
|
78
94
|
reporting.addReport({
|
|
79
95
|
type: "accesslint",
|
|
80
96
|
version: 1,
|
|
81
|
-
result
|
|
82
|
-
|
|
83
|
-
ruleCount: getActiveRules().length
|
|
84
|
-
},
|
|
85
|
-
status: hasViolations ? mode : "passed"
|
|
97
|
+
result,
|
|
98
|
+
status
|
|
86
99
|
});
|
|
87
100
|
};
|
|
88
101
|
|
package/dist/preview.cjs
CHANGED
|
@@ -1,6 +1,13 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
3
|
var core = require('@accesslint/core');
|
|
4
|
+
var previewApi = require('storybook/preview-api');
|
|
5
|
+
|
|
6
|
+
// src/preview.ts
|
|
7
|
+
|
|
8
|
+
// src/constants.ts
|
|
9
|
+
var ADDON_ID = "accesslint/a11y";
|
|
10
|
+
var RESULT_EVENT = `${ADDON_ID}/result`;
|
|
4
11
|
|
|
5
12
|
// src/preview.ts
|
|
6
13
|
core.configureRules({
|
|
@@ -41,19 +48,22 @@ var afterEach = async ({
|
|
|
41
48
|
reporting,
|
|
42
49
|
parameters,
|
|
43
50
|
viewMode,
|
|
44
|
-
tags
|
|
51
|
+
tags,
|
|
52
|
+
id
|
|
45
53
|
}) => {
|
|
46
54
|
const accesslintParam = parameters?.accesslint;
|
|
47
55
|
if (accesslintParam?.disable === true || accesslintParam?.test === "off") return;
|
|
48
56
|
if (viewMode !== "story") return;
|
|
49
57
|
const skipTags = typeof __ACCESSLINT_SKIP_TAGS__ !== "undefined" ? __ACCESSLINT_SKIP_TAGS__ : [];
|
|
50
|
-
const allSkipTags = ["
|
|
58
|
+
const allSkipTags = ["skip-accesslint", ...skipTags];
|
|
51
59
|
const matchedTag = tags?.find((t) => allSkipTags.includes(t));
|
|
52
60
|
if (matchedTag) {
|
|
61
|
+
const result2 = { skipped: true, reason: matchedTag };
|
|
62
|
+
previewApi.addons.getChannel().emit(RESULT_EVENT, { storyId: id, result: result2 });
|
|
53
63
|
reporting.addReport({
|
|
54
64
|
type: "accesslint",
|
|
55
65
|
version: 1,
|
|
56
|
-
result:
|
|
66
|
+
result: result2,
|
|
57
67
|
status: "passed"
|
|
58
68
|
});
|
|
59
69
|
return;
|
|
@@ -67,14 +77,17 @@ var afterEach = async ({
|
|
|
67
77
|
const enriched = enrichViolations(scoped);
|
|
68
78
|
const hasViolations = enriched.length > 0;
|
|
69
79
|
const mode = accesslintParam?.test === "todo" ? "warning" : "failed";
|
|
80
|
+
const status = hasViolations ? mode : "passed";
|
|
81
|
+
const result = {
|
|
82
|
+
violations: enriched,
|
|
83
|
+
ruleCount: core.getActiveRules().length
|
|
84
|
+
};
|
|
85
|
+
previewApi.addons.getChannel().emit(RESULT_EVENT, { storyId: id, result, status });
|
|
70
86
|
reporting.addReport({
|
|
71
87
|
type: "accesslint",
|
|
72
88
|
version: 1,
|
|
73
|
-
result
|
|
74
|
-
|
|
75
|
-
ruleCount: core.getActiveRules().length
|
|
76
|
-
},
|
|
77
|
-
status: hasViolations ? mode : "passed"
|
|
89
|
+
result,
|
|
90
|
+
status
|
|
78
91
|
});
|
|
79
92
|
};
|
|
80
93
|
|
package/dist/preview.d.cts
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
|
-
declare const afterEach: ({ reporting, parameters, viewMode, tags, }: {
|
|
1
|
+
declare const afterEach: ({ reporting, parameters, viewMode, tags, id, }: {
|
|
2
2
|
reporting: {
|
|
3
3
|
addReport: (report: Record<string, unknown>) => void;
|
|
4
4
|
};
|
|
5
5
|
parameters: Record<string, unknown>;
|
|
6
6
|
viewMode: string;
|
|
7
7
|
tags?: string[];
|
|
8
|
+
id?: string;
|
|
8
9
|
}) => Promise<void>;
|
|
9
10
|
|
|
10
11
|
export { afterEach };
|
package/dist/preview.d.ts
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
|
-
declare const afterEach: ({ reporting, parameters, viewMode, tags, }: {
|
|
1
|
+
declare const afterEach: ({ reporting, parameters, viewMode, tags, id, }: {
|
|
2
2
|
reporting: {
|
|
3
3
|
addReport: (report: Record<string, unknown>) => void;
|
|
4
4
|
};
|
|
5
5
|
parameters: Record<string, unknown>;
|
|
6
6
|
viewMode: string;
|
|
7
7
|
tags?: string[];
|
|
8
|
+
id?: string;
|
|
8
9
|
}) => Promise<void>;
|
|
9
10
|
|
|
10
11
|
export { afterEach };
|
package/dist/preview.js
CHANGED
|
@@ -1,4 +1,11 @@
|
|
|
1
1
|
import { configureRules, createChunkedAudit, getActiveRules, getRuleById } from '@accesslint/core';
|
|
2
|
+
import { addons } from 'storybook/preview-api';
|
|
3
|
+
|
|
4
|
+
// src/preview.ts
|
|
5
|
+
|
|
6
|
+
// src/constants.ts
|
|
7
|
+
var ADDON_ID = "accesslint/a11y";
|
|
8
|
+
var RESULT_EVENT = `${ADDON_ID}/result`;
|
|
2
9
|
|
|
3
10
|
// src/preview.ts
|
|
4
11
|
configureRules({
|
|
@@ -39,19 +46,22 @@ var afterEach = async ({
|
|
|
39
46
|
reporting,
|
|
40
47
|
parameters,
|
|
41
48
|
viewMode,
|
|
42
|
-
tags
|
|
49
|
+
tags,
|
|
50
|
+
id
|
|
43
51
|
}) => {
|
|
44
52
|
const accesslintParam = parameters?.accesslint;
|
|
45
53
|
if (accesslintParam?.disable === true || accesslintParam?.test === "off") return;
|
|
46
54
|
if (viewMode !== "story") return;
|
|
47
55
|
const skipTags = typeof __ACCESSLINT_SKIP_TAGS__ !== "undefined" ? __ACCESSLINT_SKIP_TAGS__ : [];
|
|
48
|
-
const allSkipTags = ["
|
|
56
|
+
const allSkipTags = ["skip-accesslint", ...skipTags];
|
|
49
57
|
const matchedTag = tags?.find((t) => allSkipTags.includes(t));
|
|
50
58
|
if (matchedTag) {
|
|
59
|
+
const result2 = { skipped: true, reason: matchedTag };
|
|
60
|
+
addons.getChannel().emit(RESULT_EVENT, { storyId: id, result: result2 });
|
|
51
61
|
reporting.addReport({
|
|
52
62
|
type: "accesslint",
|
|
53
63
|
version: 1,
|
|
54
|
-
result:
|
|
64
|
+
result: result2,
|
|
55
65
|
status: "passed"
|
|
56
66
|
});
|
|
57
67
|
return;
|
|
@@ -65,14 +75,17 @@ var afterEach = async ({
|
|
|
65
75
|
const enriched = enrichViolations(scoped);
|
|
66
76
|
const hasViolations = enriched.length > 0;
|
|
67
77
|
const mode = accesslintParam?.test === "todo" ? "warning" : "failed";
|
|
78
|
+
const status = hasViolations ? mode : "passed";
|
|
79
|
+
const result = {
|
|
80
|
+
violations: enriched,
|
|
81
|
+
ruleCount: getActiveRules().length
|
|
82
|
+
};
|
|
83
|
+
addons.getChannel().emit(RESULT_EVENT, { storyId: id, result, status });
|
|
68
84
|
reporting.addReport({
|
|
69
85
|
type: "accesslint",
|
|
70
86
|
version: 1,
|
|
71
|
-
result
|
|
72
|
-
|
|
73
|
-
ruleCount: getActiveRules().length
|
|
74
|
-
},
|
|
75
|
-
status: hasViolations ? mode : "passed"
|
|
87
|
+
result,
|
|
88
|
+
status
|
|
76
89
|
});
|
|
77
90
|
};
|
|
78
91
|
|
package/dist/vitest-plugin.d.cts
CHANGED
|
@@ -15,7 +15,7 @@ interface AccessLintTestOptions {
|
|
|
15
15
|
/**
|
|
16
16
|
* Tags-based filtering for which stories to audit.
|
|
17
17
|
*
|
|
18
|
-
* accesslintTest({ tags: { skip: ["
|
|
18
|
+
* accesslintTest({ tags: { skip: ["skip-accesslint"] } })
|
|
19
19
|
*
|
|
20
20
|
* Stories with any of the `skip` tags will not be audited.
|
|
21
21
|
*/
|
package/dist/vitest-plugin.d.ts
CHANGED
|
@@ -15,7 +15,7 @@ interface AccessLintTestOptions {
|
|
|
15
15
|
/**
|
|
16
16
|
* Tags-based filtering for which stories to audit.
|
|
17
17
|
*
|
|
18
|
-
* accesslintTest({ tags: { skip: ["
|
|
18
|
+
* accesslintTest({ tags: { skip: ["skip-accesslint"] } })
|
|
19
19
|
*
|
|
20
20
|
* Stories with any of the `skip` tags will not be audited.
|
|
21
21
|
*/
|
package/dist/vitest-setup.cjs
CHANGED
|
@@ -17,6 +17,12 @@ var preview_exports = {};
|
|
|
17
17
|
__export(preview_exports, {
|
|
18
18
|
afterEach: () => afterEach
|
|
19
19
|
});
|
|
20
|
+
|
|
21
|
+
// src/constants.ts
|
|
22
|
+
var ADDON_ID = "accesslint/a11y";
|
|
23
|
+
var RESULT_EVENT = `${ADDON_ID}/result`;
|
|
24
|
+
|
|
25
|
+
// src/preview.ts
|
|
20
26
|
core.configureRules({
|
|
21
27
|
disabledRules: ["accesslint-045"]
|
|
22
28
|
});
|
|
@@ -55,19 +61,22 @@ var afterEach = async ({
|
|
|
55
61
|
reporting,
|
|
56
62
|
parameters,
|
|
57
63
|
viewMode,
|
|
58
|
-
tags
|
|
64
|
+
tags,
|
|
65
|
+
id
|
|
59
66
|
}) => {
|
|
60
67
|
const accesslintParam = parameters?.accesslint;
|
|
61
68
|
if (accesslintParam?.disable === true || accesslintParam?.test === "off") return;
|
|
62
69
|
if (viewMode !== "story") return;
|
|
63
70
|
const skipTags = typeof __ACCESSLINT_SKIP_TAGS__ !== "undefined" ? __ACCESSLINT_SKIP_TAGS__ : [];
|
|
64
|
-
const allSkipTags = ["
|
|
71
|
+
const allSkipTags = ["skip-accesslint", ...skipTags];
|
|
65
72
|
const matchedTag = tags?.find((t) => allSkipTags.includes(t));
|
|
66
73
|
if (matchedTag) {
|
|
74
|
+
const result2 = { skipped: true, reason: matchedTag };
|
|
75
|
+
previewApi.addons.getChannel().emit(RESULT_EVENT, { storyId: id, result: result2 });
|
|
67
76
|
reporting.addReport({
|
|
68
77
|
type: "accesslint",
|
|
69
78
|
version: 1,
|
|
70
|
-
result:
|
|
79
|
+
result: result2,
|
|
71
80
|
status: "passed"
|
|
72
81
|
});
|
|
73
82
|
return;
|
|
@@ -81,14 +90,17 @@ var afterEach = async ({
|
|
|
81
90
|
const enriched = enrichViolations(scoped);
|
|
82
91
|
const hasViolations = enriched.length > 0;
|
|
83
92
|
const mode = accesslintParam?.test === "todo" ? "warning" : "failed";
|
|
93
|
+
const status = hasViolations ? mode : "passed";
|
|
94
|
+
const result = {
|
|
95
|
+
violations: enriched,
|
|
96
|
+
ruleCount: core.getActiveRules().length
|
|
97
|
+
};
|
|
98
|
+
previewApi.addons.getChannel().emit(RESULT_EVENT, { storyId: id, result, status });
|
|
84
99
|
reporting.addReport({
|
|
85
100
|
type: "accesslint",
|
|
86
101
|
version: 1,
|
|
87
|
-
result
|
|
88
|
-
|
|
89
|
-
ruleCount: core.getActiveRules().length
|
|
90
|
-
},
|
|
91
|
-
status: hasViolations ? mode : "passed"
|
|
102
|
+
result,
|
|
103
|
+
status
|
|
92
104
|
});
|
|
93
105
|
};
|
|
94
106
|
test.expect.extend(matchers.accesslintMatchers);
|
package/dist/vitest-setup.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { expect } from 'storybook/test';
|
|
2
2
|
import { expect as expect$1 } from 'vitest';
|
|
3
|
-
import { composeConfigs } from 'storybook/preview-api';
|
|
3
|
+
import { composeConfigs, addons } from 'storybook/preview-api';
|
|
4
4
|
import { configureRules, createChunkedAudit, getActiveRules, getRuleById } from '@accesslint/core';
|
|
5
5
|
import { accesslintMatchers } from '@accesslint/vitest/matchers';
|
|
6
6
|
|
|
@@ -15,6 +15,12 @@ var preview_exports = {};
|
|
|
15
15
|
__export(preview_exports, {
|
|
16
16
|
afterEach: () => afterEach
|
|
17
17
|
});
|
|
18
|
+
|
|
19
|
+
// src/constants.ts
|
|
20
|
+
var ADDON_ID = "accesslint/a11y";
|
|
21
|
+
var RESULT_EVENT = `${ADDON_ID}/result`;
|
|
22
|
+
|
|
23
|
+
// src/preview.ts
|
|
18
24
|
configureRules({
|
|
19
25
|
disabledRules: ["accesslint-045"]
|
|
20
26
|
});
|
|
@@ -53,19 +59,22 @@ var afterEach = async ({
|
|
|
53
59
|
reporting,
|
|
54
60
|
parameters,
|
|
55
61
|
viewMode,
|
|
56
|
-
tags
|
|
62
|
+
tags,
|
|
63
|
+
id
|
|
57
64
|
}) => {
|
|
58
65
|
const accesslintParam = parameters?.accesslint;
|
|
59
66
|
if (accesslintParam?.disable === true || accesslintParam?.test === "off") return;
|
|
60
67
|
if (viewMode !== "story") return;
|
|
61
68
|
const skipTags = typeof __ACCESSLINT_SKIP_TAGS__ !== "undefined" ? __ACCESSLINT_SKIP_TAGS__ : [];
|
|
62
|
-
const allSkipTags = ["
|
|
69
|
+
const allSkipTags = ["skip-accesslint", ...skipTags];
|
|
63
70
|
const matchedTag = tags?.find((t) => allSkipTags.includes(t));
|
|
64
71
|
if (matchedTag) {
|
|
72
|
+
const result2 = { skipped: true, reason: matchedTag };
|
|
73
|
+
addons.getChannel().emit(RESULT_EVENT, { storyId: id, result: result2 });
|
|
65
74
|
reporting.addReport({
|
|
66
75
|
type: "accesslint",
|
|
67
76
|
version: 1,
|
|
68
|
-
result:
|
|
77
|
+
result: result2,
|
|
69
78
|
status: "passed"
|
|
70
79
|
});
|
|
71
80
|
return;
|
|
@@ -79,14 +88,17 @@ var afterEach = async ({
|
|
|
79
88
|
const enriched = enrichViolations(scoped);
|
|
80
89
|
const hasViolations = enriched.length > 0;
|
|
81
90
|
const mode = accesslintParam?.test === "todo" ? "warning" : "failed";
|
|
91
|
+
const status = hasViolations ? mode : "passed";
|
|
92
|
+
const result = {
|
|
93
|
+
violations: enriched,
|
|
94
|
+
ruleCount: getActiveRules().length
|
|
95
|
+
};
|
|
96
|
+
addons.getChannel().emit(RESULT_EVENT, { storyId: id, result, status });
|
|
82
97
|
reporting.addReport({
|
|
83
98
|
type: "accesslint",
|
|
84
99
|
version: 1,
|
|
85
|
-
result
|
|
86
|
-
|
|
87
|
-
ruleCount: getActiveRules().length
|
|
88
|
-
},
|
|
89
|
-
status: hasViolations ? mode : "passed"
|
|
100
|
+
result,
|
|
101
|
+
status
|
|
90
102
|
});
|
|
91
103
|
};
|
|
92
104
|
expect.extend(accesslintMatchers);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@accesslint/storybook-addon",
|
|
3
|
-
"version": "0.8.
|
|
3
|
+
"version": "0.8.4",
|
|
4
4
|
"description": "Catch accessibility violations in your Storybook stories as you develop",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"publishConfig": {
|
|
@@ -59,7 +59,7 @@
|
|
|
59
59
|
},
|
|
60
60
|
"dependencies": {
|
|
61
61
|
"@accesslint/core": "^0.6.5",
|
|
62
|
-
"@accesslint/vitest": "^0.1.
|
|
62
|
+
"@accesslint/vitest": "^0.1.4"
|
|
63
63
|
},
|
|
64
64
|
"devDependencies": {
|
|
65
65
|
"react": "^18.2.0",
|