testaro 78.0.8 → 78.4.0
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/.gitattributes +94 -0
- package/.github/workflows/ci.yml +58 -0
- package/.github/workflows/publish.yml +49 -0
- package/.github/workflows/typescript.yml +35 -0
- package/AGENTS.md +2 -2
- package/CLAUDE.md +24 -18
- package/CONTAINERS.md +9 -6
- package/CONTRIBUTING.md +29 -3
- package/Dockerfile +1 -1
- package/README.md +73 -19
- package/UPGRADES.md +4 -0
- package/actSpecs-doc.md +13 -1
- package/actSpecs.js +29 -5
- package/call.js +6 -5
- package/docker-compose.yml +8 -2
- package/docs/checkpoint-scanning.md +199 -0
- package/docs/standard-result-outcome.md +165 -0
- package/env.example +44 -10
- package/eslint.config.mjs +101 -0
- package/netWatch.js +372 -222
- package/package.json +46 -31
- package/pour/README.md +47 -0
- package/pour/pour.min.js +8 -0
- package/procs/actDo.js +808 -0
- package/procs/catalog.d.ts +17 -0
- package/procs/catalog.js +312 -221
- package/procs/catalog.ts +398 -0
- package/procs/checkpoint.js +110 -0
- package/procs/config.d.ts +35 -0
- package/procs/config.js +62 -0
- package/procs/dateTime.js +2 -1
- package/procs/doActs.js +442 -849
- package/procs/doTestAct.js +27 -121
- package/procs/flow.js +221 -0
- package/procs/generateRuleRegistry.js +94 -0
- package/procs/getSource.d.ts +26 -0
- package/procs/job.js +115 -1
- package/procs/launch.d.ts +40 -0
- package/procs/launch.js +239 -108
- package/procs/nu.d.ts +48 -0
- package/procs/scope.js +196 -0
- package/procs/shoot.d.ts +33 -0
- package/procs/standard.d.ts +18 -0
- package/procs/standard.js +83 -0
- package/procs/standard.ts +126 -0
- package/procs/testAct.js +145 -0
- package/procs/testaro.d.ts +20 -0
- package/procs/testaro.js +236 -189
- package/procs/testaro.ts +321 -0
- package/procs/userPath.js +126 -0
- package/procs/xPath.d.ts +4 -0
- package/procs/xPath.js +81 -69
- package/procs/xPath.ts +106 -0
- package/procs/xPathScript.d.ts +6 -0
- package/procs/xPathScript.js +70 -0
- package/run.js +3 -2
- package/surea11y/README.md +44 -0
- package/surea11y/surea11y.browser.js +14 -0
- package/testaro/adbID.d.ts +3 -0
- package/testaro/adbID.js +38 -41
- package/testaro/adbID.ts +66 -0
- package/testaro/allCapStyle.d.ts +3 -0
- package/testaro/allCapStyle.js +31 -34
- package/testaro/allCapStyle.ts +55 -0
- package/testaro/allCaps.d.ts +16 -0
- package/testaro/allCaps.js +179 -151
- package/testaro/allCaps.ts +228 -0
- package/testaro/allHidden.d.ts +13 -0
- package/testaro/allHidden.js +29 -30
- package/testaro/allHidden.ts +50 -0
- package/testaro/allSlanted.d.ts +3 -0
- package/testaro/allSlanted.js +30 -33
- package/testaro/allSlanted.ts +54 -0
- package/testaro/altScheme.d.ts +3 -0
- package/testaro/altScheme.js +27 -30
- package/testaro/altScheme.ts +50 -0
- package/testaro/attVal.d.ts +3 -0
- package/testaro/attVal.js +20 -21
- package/testaro/attVal.ts +52 -0
- package/testaro/autocomplete.d.ts +3 -0
- package/testaro/autocomplete.js +59 -75
- package/testaro/autocomplete.ts +101 -0
- package/testaro/bulk.d.ts +13 -0
- package/testaro/bulk.js +32 -33
- package/testaro/bulk.ts +55 -0
- package/testaro/buttonMenu.d.ts +9 -0
- package/testaro/buttonMenu.js +317 -319
- package/testaro/buttonMenu.ts +391 -0
- package/testaro/captionLoc.d.ts +3 -0
- package/testaro/captionLoc.js +17 -20
- package/testaro/captionLoc.ts +40 -0
- package/testaro/datalistRef.d.ts +3 -0
- package/testaro/datalistRef.js +33 -36
- package/testaro/datalistRef.ts +55 -0
- package/testaro/distortion.d.ts +3 -0
- package/testaro/distortion.js +57 -26
- package/testaro/distortion.ts +81 -0
- package/testaro/docType.d.ts +15 -0
- package/testaro/docType.js +25 -25
- package/testaro/docType.ts +45 -0
- package/testaro/dupAtt.d.ts +16 -0
- package/testaro/dupAtt.js +113 -104
- package/testaro/dupAtt.ts +144 -0
- package/testaro/elements.d.ts +6 -0
- package/testaro/elements.js +153 -153
- package/testaro/elements.ts +215 -0
- package/testaro/embAc.d.ts +3 -0
- package/testaro/embAc.js +19 -20
- package/testaro/embAc.ts +40 -0
- package/testaro/focAll.d.ts +13 -0
- package/testaro/focAll.js +185 -191
- package/testaro/focAll.ts +217 -0
- package/testaro/focAndOp.d.ts +3 -0
- package/testaro/focAndOp.js +100 -104
- package/testaro/focAndOp.ts +128 -0
- package/testaro/focInd.d.ts +3 -0
- package/testaro/focInd.js +64 -66
- package/testaro/focInd.ts +96 -0
- package/testaro/focVis.d.ts +3 -0
- package/testaro/focVis.js +28 -30
- package/testaro/focVis.ts +52 -0
- package/testaro/headEl.d.ts +10 -0
- package/testaro/headEl.js +61 -62
- package/testaro/headEl.ts +82 -0
- package/testaro/headingAmb.d.ts +3 -0
- package/testaro/headingAmb.js +54 -63
- package/testaro/headingAmb.ts +72 -0
- package/testaro/hovInd.d.ts +12 -0
- package/testaro/hovInd.js +163 -130
- package/testaro/hovInd.ts +199 -0
- package/testaro/hover.d.ts +3 -0
- package/testaro/hover.js +155 -126
- package/testaro/hover.ts +154 -0
- package/testaro/hr.d.ts +3 -0
- package/testaro/hr.js +14 -17
- package/testaro/hr.ts +36 -0
- package/testaro/imageLink.d.ts +3 -0
- package/testaro/imageLink.js +17 -20
- package/testaro/imageLink.ts +42 -0
- package/testaro/labClash.d.ts +3 -0
- package/testaro/labClash.js +31 -33
- package/testaro/labClash.ts +54 -0
- package/testaro/legendLoc.d.ts +3 -0
- package/testaro/legendLoc.js +17 -20
- package/testaro/legendLoc.ts +42 -0
- package/testaro/lineHeight.d.ts +3 -0
- package/testaro/lineHeight.js +43 -48
- package/testaro/lineHeight.ts +70 -0
- package/testaro/linkAmb.d.ts +7 -0
- package/testaro/linkAmb.js +79 -80
- package/testaro/linkAmb.ts +105 -0
- package/testaro/linkExt.d.ts +3 -0
- package/testaro/linkExt.js +13 -16
- package/testaro/linkExt.ts +35 -0
- package/testaro/linkOldAtt.d.ts +3 -0
- package/testaro/linkOldAtt.js +25 -28
- package/testaro/linkOldAtt.ts +48 -0
- package/testaro/linkTo.d.ts +3 -0
- package/testaro/linkTo.js +22 -22
- package/testaro/linkTo.ts +43 -0
- package/testaro/linkUl.d.ts +3 -0
- package/testaro/linkUl.js +30 -34
- package/testaro/linkUl.ts +54 -0
- package/testaro/miniText.d.ts +3 -0
- package/testaro/miniText.js +41 -44
- package/testaro/miniText.ts +68 -0
- package/testaro/motion.d.ts +10 -0
- package/testaro/motion.js +92 -96
- package/testaro/motion.ts +125 -0
- package/testaro/nonTable.d.ts +3 -0
- package/testaro/nonTable.js +39 -45
- package/testaro/nonTable.ts +66 -0
- package/testaro/optRoleSel.d.ts +3 -0
- package/testaro/optRoleSel.js +16 -19
- package/testaro/optRoleSel.ts +41 -0
- package/testaro/phOnly.d.ts +3 -0
- package/testaro/phOnly.js +18 -21
- package/testaro/phOnly.ts +43 -0
- package/testaro/pseudoP.d.ts +3 -0
- package/testaro/pseudoP.js +36 -38
- package/testaro/pseudoP.ts +59 -0
- package/testaro/radioSet.d.ts +3 -0
- package/testaro/radioSet.js +57 -59
- package/testaro/radioSet.ts +79 -0
- package/testaro/registry.d.ts +63 -0
- package/testaro/registry.js +67 -0
- package/testaro/registry.ts +141 -0
- package/testaro/role.d.ts +3 -0
- package/testaro/role.js +27 -29
- package/testaro/role.ts +53 -0
- package/testaro/secHeading.d.ts +3 -0
- package/testaro/secHeading.js +30 -33
- package/testaro/secHeading.ts +53 -0
- package/testaro/styleDiff.d.ts +25 -0
- package/testaro/styleDiff.js +248 -252
- package/testaro/styleDiff.ts +303 -0
- package/testaro/tabNav.d.ts +33 -0
- package/testaro/tabNav.js +272 -342
- package/testaro/tabNav.ts +454 -0
- package/testaro/targetsNear.d.ts +9 -0
- package/testaro/targetsNear.js +130 -132
- package/testaro/targetsNear.ts +160 -0
- package/testaro/textNodes.d.ts +6 -0
- package/testaro/textNodes.js +139 -135
- package/testaro/textNodes.ts +185 -0
- package/testaro/textSem.d.ts +3 -0
- package/testaro/textSem.js +25 -28
- package/testaro/textSem.ts +47 -0
- package/testaro/title.d.ts +9 -0
- package/testaro/title.js +16 -13
- package/testaro/title.ts +31 -0
- package/testaro/titledEl.d.ts +3 -0
- package/testaro/titledEl.js +15 -18
- package/testaro/titledEl.ts +38 -0
- package/testaro/zIndex.d.ts +3 -0
- package/testaro/zIndex.js +19 -22
- package/testaro/zIndex.ts +42 -0
- package/tests/alfa.d.ts +45 -0
- package/tests/alfa.js +138 -141
- package/tests/alfa.ts +214 -0
- package/tests/aslint.d.ts +33 -0
- package/tests/aslint.js +272 -249
- package/tests/aslint.ts +301 -0
- package/tests/axe.d.ts +27 -0
- package/tests/axe.js +199 -200
- package/tests/axe.ts +277 -0
- package/tests/ed11y.d.ts +28 -0
- package/tests/ed11y.js +141 -99
- package/tests/ed11y.ts +178 -0
- package/tests/htmlcs.d.ts +21 -0
- package/tests/htmlcs.js +174 -140
- package/tests/htmlcs.ts +181 -0
- package/tests/ibm.d.ts +52 -0
- package/tests/ibm.js +164 -166
- package/tests/ibm.ts +251 -0
- package/tests/nuVal.d.ts +13 -0
- package/tests/nuVal.js +107 -112
- package/tests/nuVal.ts +145 -0
- package/tests/nuVnu.d.ts +15 -0
- package/tests/nuVnu.js +141 -111
- package/tests/nuVnu.ts +144 -0
- package/tests/pour.d.ts +31 -0
- package/tests/pour.js +242 -0
- package/tests/pour.ts +273 -0
- package/tests/qualWeb.d.ts +39 -0
- package/tests/qualWeb.js +302 -272
- package/tests/qualWeb.ts +415 -0
- package/tests/surea11y.d.ts +33 -0
- package/tests/surea11y.js +288 -0
- package/tests/surea11y.ts +334 -0
- package/tests/testaro.d.ts +25 -0
- package/tests/testaro.js +745 -652
- package/tests/testaro.ts +862 -0
- package/tests/wave.d.ts +46 -0
- package/tests/wave.js +166 -177
- package/tests/wave.ts +252 -0
- package/tsconfig.json +17 -0
- package/types.d.ts +243 -0
- package/types.js +10 -0
- package/types.ts +376 -0
- package/validation/act/README.md +46 -0
- package/validation/act/capture.js +424 -0
- package/validation/act/chromium-issue-draft.md +66 -0
- package/validation/act/fp-triage-2026-08-22.md +86 -0
- package/validation/act/isolation-notes.md +159 -0
- package/validation/act/playwright-issue-draft.md +73 -0
- package/validation/act/propose-mappings.js +0 -0
- package/validation/act/repro-cdp-raw.js +105 -0
- package/validation/act/repro-metarefresh.js +65 -0
- package/validation/act/score.js +184 -0
- package/validation/act/stage3a-stress-report.md +69 -0
- package/validation/act/stage3b-mapping-proposals.md +94 -0
- package/validation/act/stage3b-triage-draft.md +138 -0
- package/validation/act/surea11y-track-a-2026-09-01.md +50 -0
- package/validation/executors/netWatch.js +180 -90
- package/validation/executors/test.js +17 -2
- package/validation/executors/tests.js +118 -10
- package/validation/jobs/reports/raw/260901T1000-surea11y-validation.json +964 -0
- package/validation/jobs/todo/240101T1200-simple-example.json +14 -6
- package/validation/jobs/todo/240101T1300-shoot-example.json +2 -1
- package/validation/jobs/todo/260821T1900-pour-validation.json +45 -0
- package/validation/jobs/todo/260901T1000-surea11y-validation.json +45 -0
- package/validation/knownFailures.json +1 -0
- package/validation/tests/jobProperties/adbID.json +27 -2
- package/validation/tests/jobProperties/{focOp.json → allCapStyle.json} +56 -53
- package/validation/tests/jobProperties/allCaps.json +25 -0
- package/validation/tests/jobProperties/allHidden.json +133 -13
- package/validation/tests/jobProperties/allSlanted.json +3 -3
- package/validation/tests/jobProperties/altScheme.json +23 -8
- package/validation/tests/jobProperties/attVal.json +57 -57
- package/validation/tests/jobProperties/autocomplete.json +11 -1
- package/validation/tests/jobProperties/bulk.json +6 -1
- package/validation/tests/jobProperties/buttonMenu.json +63 -42
- package/validation/tests/jobProperties/captionLoc.json +1 -6
- package/validation/tests/jobProperties/checkpoint-browser.json +401 -0
- package/validation/tests/jobProperties/checkpoint-page.json +397 -0
- package/validation/tests/jobProperties/checkpoint.json +395 -0
- package/validation/tests/jobProperties/datalistRef.json +20 -5
- package/validation/tests/jobProperties/distortion.json +28 -3
- package/validation/tests/jobProperties/docType.json +2 -2
- package/validation/tests/jobProperties/dupAtt.json +48 -33
- package/validation/tests/jobProperties/elements.json +28 -28
- package/validation/tests/jobProperties/embAc.json +36 -31
- package/validation/tests/jobProperties/focAndOp.json +284 -0
- package/validation/tests/jobProperties/focInd.json +34 -34
- package/validation/tests/jobProperties/focVis.json +1 -1
- package/validation/tests/jobProperties/hover.json +39 -37
- package/validation/tests/jobProperties/hr.json +13 -3
- package/validation/tests/jobProperties/imageLink.json +0 -5
- package/validation/tests/jobProperties/labClash.json +68 -33
- package/validation/tests/jobProperties/legendLoc.json +1 -6
- package/validation/tests/jobProperties/lineHeight.json +2 -2
- package/validation/tests/jobProperties/linkAmb.json +13 -18
- package/validation/tests/jobProperties/linkExt.json +1 -1
- package/validation/tests/jobProperties/linkOldAtt.json +12 -2
- package/validation/tests/jobProperties/linkTo.json +1 -1
- package/validation/tests/jobProperties/linkUl.json +65 -65
- package/validation/tests/jobProperties/miniText.json +7 -2
- package/validation/tests/jobProperties/motion.json +4 -50
- package/validation/tests/jobProperties/nonTable.json +48 -3
- package/validation/tests/jobProperties/optRoleSel.json +12 -2
- package/validation/tests/jobProperties/phOnly.json +6 -16
- package/validation/tests/jobProperties/pseudoP.json +17 -2
- package/validation/tests/jobProperties/radioSet.json +30 -30
- package/validation/tests/jobProperties/role.json +25 -5
- package/validation/tests/jobProperties/secHeading.json +26 -21
- package/validation/tests/jobProperties/styleDiff.json +35 -5
- package/validation/tests/jobProperties/tabNav.json +3 -1
- package/validation/tests/jobProperties/targetsNear.json +237 -0
- package/validation/tests/jobProperties/textNodes.json +29 -29
- package/validation/tests/jobProperties/textSem.json +26 -1
- package/validation/tests/jobProperties/title.json +12 -2
- package/validation/tests/jobProperties/titledEl.json +39 -9
- package/validation/tests/jobProperties/userPath.json +317 -0
- package/validation/tests/jobProperties/zIndex.json +40 -35
- package/validation/tests/targets/allCapStyle/index.html +26 -0
- package/validation/tests/targets/checkpoint/index.html +38 -0
- package/validation/tests/targets/datalistRef/index.html +1 -1
- package/validation/tests/targets/focAndOp/bad.html +29 -0
- package/validation/tests/targets/{focOp → focAndOp}/good.html +3 -1
- package/validation/tests/targets/focInd/bad.html +2 -1
- package/validation/tests/targets/headEl/index.html +10 -1
- package/validation/tests/targets/{targetSmall → targetsNear}/index.html +15 -1
- package/validation/tests/targets/userPath/index.html +42 -0
- package/validation/validateTest.js +61 -9
- package/.claude/settings.local.json +0 -11
- package/.eslintrc.json +0 -41
- package/htmlcs/.eslintrc.json +0 -67
- package/validation/tests/jobProperties/linkTitle.json +0 -127
- package/validation/tests/jobProperties/opFoc.json +0 -164
- package/validation/tests/jobProperties/targetSmall.json +0 -152
- package/validation/tests/jobProperties/targetTiny.json +0 -142
- package/validation/tests/targets/focOp/bad.html +0 -25
- package/validation/tests/targets/linkTitle/index.html +0 -24
- package/validation/tests/targets/opFoc/bad.html +0 -26
- package/validation/tests/targets/opFoc/good.html +0 -23
package/testaro/focVis.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
"use strict";
|
|
1
2
|
/*
|
|
2
3
|
© 2022–2025 CVS Health and/or one of its affiliates. All rights reserved.
|
|
3
4
|
© 2026 Jeff Witt.
|
|
@@ -8,41 +9,38 @@
|
|
|
8
9
|
|
|
9
10
|
SPDX-License-Identifier: MIT
|
|
10
11
|
*/
|
|
11
|
-
|
|
12
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
13
|
+
exports.reporter = void 0;
|
|
14
|
+
const testaro_1 = require("../procs/testaro");
|
|
12
15
|
/*
|
|
13
16
|
focVis
|
|
14
17
|
Derived from the bbc-a11y elementsMustBeVisibleOnFocus test.
|
|
15
18
|
This test reports links that are at least partly off the display when focused.
|
|
19
|
+
Compiled to focVis.js by tsc (issue #73); edit this file, not the emitted one.
|
|
16
20
|
*/
|
|
17
|
-
|
|
18
|
-
// IMPORTS
|
|
19
|
-
|
|
20
|
-
const {doTest} = require('../procs/testaro');
|
|
21
|
-
|
|
22
21
|
// FUNCTIONS
|
|
23
|
-
|
|
24
22
|
// Runs the test and returns the result.
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
const
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
page, report, withItems, 'focVis', 'body a', whats, 2, getBadWhat.toString()
|
|
47
|
-
);
|
|
23
|
+
const reporter = async (page, report, _, withItems) => {
|
|
24
|
+
// The candidate selector guarantees focusable HTML elements.
|
|
25
|
+
const getBadWhat = (element) => {
|
|
26
|
+
const isVisible = element.checkVisibility({
|
|
27
|
+
contentVisibilityAuto: true,
|
|
28
|
+
opacityProperty: true,
|
|
29
|
+
visibilityProperty: true
|
|
30
|
+
});
|
|
31
|
+
// If the element is visible:
|
|
32
|
+
if (isVisible) {
|
|
33
|
+
// Focus it.
|
|
34
|
+
element.focus();
|
|
35
|
+
const box = element.getBoundingClientRect();
|
|
36
|
+
// If it violates the rule:
|
|
37
|
+
if (box.x < 0 || box.y < 0) {
|
|
38
|
+
// Return a violation description.
|
|
39
|
+
return 'Upper left corner of the element is above or to the left of the display';
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
};
|
|
43
|
+
const whats = 'Visible links are above or to the left of the display';
|
|
44
|
+
return await (0, testaro_1.doTest)(page, report, withItems, 'focVis', 'body a', whats, 2, getBadWhat.toString());
|
|
48
45
|
};
|
|
46
|
+
exports.reporter = reporter;
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
/*
|
|
2
|
+
© 2022–2025 CVS Health and/or one of its affiliates. All rights reserved.
|
|
3
|
+
© 2026 Jeff Witt.
|
|
4
|
+
© 2025–2026 Jonathan Robert Pool.
|
|
5
|
+
|
|
6
|
+
Licensed under the MIT License. See LICENSE file at the project root or
|
|
7
|
+
https://opensource.org/license/mit/ for details.
|
|
8
|
+
|
|
9
|
+
SPDX-License-Identifier: MIT
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
// IMPORTS
|
|
13
|
+
|
|
14
|
+
import type {Page} from 'playwright';
|
|
15
|
+
import {doTest} from '../procs/testaro';
|
|
16
|
+
import type {BadWhat, Report} from '../types';
|
|
17
|
+
|
|
18
|
+
/*
|
|
19
|
+
focVis
|
|
20
|
+
Derived from the bbc-a11y elementsMustBeVisibleOnFocus test.
|
|
21
|
+
This test reports links that are at least partly off the display when focused.
|
|
22
|
+
Compiled to focVis.js by tsc (issue #73); edit this file, not the emitted one.
|
|
23
|
+
*/
|
|
24
|
+
|
|
25
|
+
// FUNCTIONS
|
|
26
|
+
|
|
27
|
+
// Runs the test and returns the result.
|
|
28
|
+
export const reporter = async (page: Page, report: Report, _: unknown, withItems: boolean) => {
|
|
29
|
+
// The candidate selector guarantees focusable HTML elements.
|
|
30
|
+
const getBadWhat = (element: HTMLElement): BadWhat => {
|
|
31
|
+
const isVisible = element.checkVisibility({
|
|
32
|
+
contentVisibilityAuto: true,
|
|
33
|
+
opacityProperty: true,
|
|
34
|
+
visibilityProperty: true
|
|
35
|
+
});
|
|
36
|
+
// If the element is visible:
|
|
37
|
+
if (isVisible) {
|
|
38
|
+
// Focus it.
|
|
39
|
+
element.focus();
|
|
40
|
+
const box = element.getBoundingClientRect();
|
|
41
|
+
// If it violates the rule:
|
|
42
|
+
if (box.x < 0 || box.y < 0) {
|
|
43
|
+
// Return a violation description.
|
|
44
|
+
return 'Upper left corner of the element is above or to the left of the display';
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
};
|
|
48
|
+
const whats = 'Visible links are above or to the left of the display';
|
|
49
|
+
return await doTest(
|
|
50
|
+
page, report, withItems, 'focVis', 'body a', whats, 2, getBadWhat.toString()
|
|
51
|
+
);
|
|
52
|
+
};
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import type { Page } from 'playwright';
|
|
2
|
+
import type { Report, StandardInstance } from '../types';
|
|
3
|
+
export declare const reporter: (page: Page, report: Report) => Promise<{
|
|
4
|
+
data: {
|
|
5
|
+
total: number;
|
|
6
|
+
badTagNames: string[];
|
|
7
|
+
};
|
|
8
|
+
totals: number[];
|
|
9
|
+
standardInstances: StandardInstance[];
|
|
10
|
+
}>;
|
package/testaro/headEl.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
"use strict";
|
|
1
2
|
/*
|
|
2
3
|
© 2023–2024 CVS Health and/or one of its affiliates. All rights reserved.
|
|
3
4
|
© 2026 Jeff Witt.
|
|
@@ -7,73 +8,71 @@
|
|
|
7
8
|
|
|
8
9
|
SPDX-License-Identifier: MIT
|
|
9
10
|
*/
|
|
10
|
-
|
|
11
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
+
exports.reporter = void 0;
|
|
13
|
+
const xPath_1 = require("../procs/xPath");
|
|
11
14
|
/*
|
|
12
15
|
headEl
|
|
13
16
|
Related to ASLint rule elements-not-allowed-in-head.
|
|
14
|
-
This test reports invalid descendants of the head of the document.
|
|
17
|
+
This test reports invalid descendants of the head of the document. Compiled to headEl.js by
|
|
18
|
+
tsc (issue #73); edit this file, not the emitted one.
|
|
15
19
|
*/
|
|
16
|
-
|
|
17
|
-
// IMPORTS
|
|
18
|
-
|
|
19
|
-
const {getXPathCatalogIndex} = require('../procs/xPath');
|
|
20
|
-
|
|
21
20
|
// ########## FUNCTIONS
|
|
22
|
-
|
|
23
21
|
// Runs the test and returns the result.
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
});
|
|
42
|
-
const validTagNames = [
|
|
43
|
-
'BASE',
|
|
44
|
-
'LINK',
|
|
45
|
-
'META',
|
|
46
|
-
'SCRIPT',
|
|
47
|
-
'STYLE',
|
|
48
|
-
'TITLE',
|
|
49
|
-
'NOSCRIPT',
|
|
50
|
-
'TEMPLATE'
|
|
51
|
-
];
|
|
52
|
-
// For each head child:
|
|
53
|
-
headElTagNames.forEach(tagName => {
|
|
54
|
-
// If it is invalid:
|
|
55
|
-
if (! validTagNames.includes(tagName)) {
|
|
56
|
-
// Add its tag name to the result.
|
|
57
|
-
data.total++;
|
|
58
|
-
data.badTagNames.push(tagName);
|
|
59
|
-
}
|
|
60
|
-
});
|
|
61
|
-
// If there are any instances:
|
|
62
|
-
if (data.total) {
|
|
63
|
-
// Add a summary instance to the standard instances.
|
|
64
|
-
standardInstances.push({
|
|
65
|
-
ruleID: 'headEl',
|
|
66
|
-
what: `Invalid elements within the head: ${data.badTagNames.join(', ')}`,
|
|
67
|
-
ordinalSeverity: 2,
|
|
68
|
-
count: data.total,
|
|
69
|
-
catalogIndex: getXPathCatalogIndex(report, '/html/head')
|
|
22
|
+
const reporter = async (page, report) => {
|
|
23
|
+
// Initialize the data and standard result.
|
|
24
|
+
const data = {
|
|
25
|
+
total: 0,
|
|
26
|
+
badTagNames: []
|
|
27
|
+
};
|
|
28
|
+
let totals = [];
|
|
29
|
+
const standardInstances = [];
|
|
30
|
+
// Get the tag names of the elements in the head, even if the head tags are omitted.
|
|
31
|
+
const headElTagNames = await page.evaluate(() => {
|
|
32
|
+
const head = document.head;
|
|
33
|
+
const headChildren = head.children;
|
|
34
|
+
const tagNames = [];
|
|
35
|
+
for (const child of headChildren) {
|
|
36
|
+
tagNames.push(child.tagName);
|
|
37
|
+
}
|
|
38
|
+
return tagNames;
|
|
70
39
|
});
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
40
|
+
const validTagNames = [
|
|
41
|
+
'BASE',
|
|
42
|
+
'LINK',
|
|
43
|
+
'META',
|
|
44
|
+
'SCRIPT',
|
|
45
|
+
'STYLE',
|
|
46
|
+
'TITLE',
|
|
47
|
+
'NOSCRIPT',
|
|
48
|
+
'TEMPLATE'
|
|
49
|
+
];
|
|
50
|
+
// For each head child:
|
|
51
|
+
headElTagNames.forEach(tagName => {
|
|
52
|
+
// If it is invalid:
|
|
53
|
+
if (!validTagNames.includes(tagName)) {
|
|
54
|
+
// Add its tag name to the result.
|
|
55
|
+
data.total++;
|
|
56
|
+
data.badTagNames.push(tagName);
|
|
57
|
+
}
|
|
58
|
+
});
|
|
59
|
+
// If there are any instances:
|
|
60
|
+
if (data.total) {
|
|
61
|
+
// Add a summary instance to the standard instances.
|
|
62
|
+
standardInstances.push({
|
|
63
|
+
ruleID: 'headEl',
|
|
64
|
+
what: `Invalid elements within the head: ${data.badTagNames.join(', ')}`,
|
|
65
|
+
ordinalSeverity: 2,
|
|
66
|
+
count: data.total,
|
|
67
|
+
catalogIndex: (0, xPath_1.getXPathCatalogIndex)(report, '/html/head')
|
|
68
|
+
});
|
|
69
|
+
}
|
|
70
|
+
totals = [0, 0, data.total, 0];
|
|
71
|
+
// Return the data.
|
|
72
|
+
return {
|
|
73
|
+
data,
|
|
74
|
+
totals,
|
|
75
|
+
standardInstances
|
|
76
|
+
};
|
|
79
77
|
};
|
|
78
|
+
exports.reporter = reporter;
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
/*
|
|
2
|
+
© 2023–2024 CVS Health and/or one of its affiliates. All rights reserved.
|
|
3
|
+
© 2026 Jeff Witt.
|
|
4
|
+
© 2025–2026 Jonathan Robert Pool.
|
|
5
|
+
|
|
6
|
+
Licensed under the MIT License. See LICENSE file at the project root or https://opensource.org/license/mit/ for details.
|
|
7
|
+
|
|
8
|
+
SPDX-License-Identifier: MIT
|
|
9
|
+
*/
|
|
10
|
+
|
|
11
|
+
// IMPORTS
|
|
12
|
+
|
|
13
|
+
import type {Page} from 'playwright';
|
|
14
|
+
import {getXPathCatalogIndex} from '../procs/xPath';
|
|
15
|
+
import type {Report, StandardInstance} from '../types';
|
|
16
|
+
|
|
17
|
+
/*
|
|
18
|
+
headEl
|
|
19
|
+
Related to ASLint rule elements-not-allowed-in-head.
|
|
20
|
+
This test reports invalid descendants of the head of the document. Compiled to headEl.js by
|
|
21
|
+
tsc (issue #73); edit this file, not the emitted one.
|
|
22
|
+
*/
|
|
23
|
+
|
|
24
|
+
// ########## FUNCTIONS
|
|
25
|
+
|
|
26
|
+
// Runs the test and returns the result.
|
|
27
|
+
export const reporter = async (page: Page, report: Report) => {
|
|
28
|
+
// Initialize the data and standard result.
|
|
29
|
+
const data: {total: number; badTagNames: string[]} = {
|
|
30
|
+
total: 0,
|
|
31
|
+
badTagNames: []
|
|
32
|
+
};
|
|
33
|
+
let totals: number[] = [];
|
|
34
|
+
const standardInstances: StandardInstance[] = [];
|
|
35
|
+
// Get the tag names of the elements in the head, even if the head tags are omitted.
|
|
36
|
+
const headElTagNames = await page.evaluate(() => {
|
|
37
|
+
const head = document.head;
|
|
38
|
+
const headChildren = head.children;
|
|
39
|
+
const tagNames: string[] = [];
|
|
40
|
+
for (const child of headChildren) {
|
|
41
|
+
tagNames.push(child.tagName);
|
|
42
|
+
}
|
|
43
|
+
return tagNames;
|
|
44
|
+
});
|
|
45
|
+
const validTagNames = [
|
|
46
|
+
'BASE',
|
|
47
|
+
'LINK',
|
|
48
|
+
'META',
|
|
49
|
+
'SCRIPT',
|
|
50
|
+
'STYLE',
|
|
51
|
+
'TITLE',
|
|
52
|
+
'NOSCRIPT',
|
|
53
|
+
'TEMPLATE'
|
|
54
|
+
];
|
|
55
|
+
// For each head child:
|
|
56
|
+
headElTagNames.forEach(tagName => {
|
|
57
|
+
// If it is invalid:
|
|
58
|
+
if (! validTagNames.includes(tagName)) {
|
|
59
|
+
// Add its tag name to the result.
|
|
60
|
+
data.total++;
|
|
61
|
+
data.badTagNames.push(tagName);
|
|
62
|
+
}
|
|
63
|
+
});
|
|
64
|
+
// If there are any instances:
|
|
65
|
+
if (data.total) {
|
|
66
|
+
// Add a summary instance to the standard instances.
|
|
67
|
+
standardInstances.push({
|
|
68
|
+
ruleID: 'headEl',
|
|
69
|
+
what: `Invalid elements within the head: ${data.badTagNames.join(', ')}`,
|
|
70
|
+
ordinalSeverity: 2,
|
|
71
|
+
count: data.total,
|
|
72
|
+
catalogIndex: getXPathCatalogIndex(report, '/html/head')
|
|
73
|
+
});
|
|
74
|
+
}
|
|
75
|
+
totals = [0, 0, data.total, 0];
|
|
76
|
+
// Return the data.
|
|
77
|
+
return {
|
|
78
|
+
data,
|
|
79
|
+
totals,
|
|
80
|
+
standardInstances
|
|
81
|
+
};
|
|
82
|
+
};
|
package/testaro/headingAmb.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
"use strict";
|
|
1
2
|
/*
|
|
2
3
|
© 2023–2024 CVS Health and/or one of its affiliates. All rights reserved.
|
|
3
4
|
© 2026 Jeff Witt.
|
|
@@ -7,70 +8,60 @@
|
|
|
7
8
|
|
|
8
9
|
SPDX-License-Identifier: MIT
|
|
9
10
|
*/
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
Related to ASLint rule headings-sibling-unique.
|
|
14
|
-
This test reports adjacent headings with the same levels and text contents.
|
|
15
|
-
*/
|
|
16
|
-
|
|
17
|
-
// IMPORTS
|
|
18
|
-
|
|
19
|
-
const {doTest} = require('../procs/testaro');
|
|
20
|
-
|
|
11
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
+
exports.reporter = void 0;
|
|
13
|
+
const testaro_1 = require("../procs/testaro");
|
|
21
14
|
// ########## FUNCTIONS
|
|
22
|
-
|
|
23
15
|
// Runs the test and returns the result.
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
16
|
+
const reporter = async (page, report, _, withItems) => {
|
|
17
|
+
const getBadWhat = element => {
|
|
18
|
+
const { tagName } = element;
|
|
19
|
+
const level = tagName[1];
|
|
20
|
+
const textContent = element.textContent.trim().replace(/\s+/g, ' ');
|
|
21
|
+
const headingTagNames = ['H1', 'H2', 'H3', 'H4', 'H5', 'H6'];
|
|
22
|
+
// Initialize the inspected element as the previous element sibling of the element.
|
|
23
|
+
let inspectedElement = element.previousElementSibling;
|
|
24
|
+
// As long as the inspected element exists:
|
|
25
|
+
while (inspectedElement) {
|
|
26
|
+
const inspectedTagName = inspectedElement.tagName;
|
|
27
|
+
// If it is a heading:
|
|
28
|
+
if (headingTagNames.includes(inspectedTagName)) {
|
|
29
|
+
// If it is inferior to the element:
|
|
30
|
+
if (inspectedTagName[1] > level) {
|
|
31
|
+
// Stop inspecting it and start inspecting its previous sibling.
|
|
32
|
+
inspectedElement = inspectedElement.previousElementSibling;
|
|
33
|
+
continue;
|
|
34
|
+
}
|
|
35
|
+
// Otherwise, if its level is the same as that of the element:
|
|
36
|
+
else if (inspectedTagName === tagName) {
|
|
37
|
+
const inspectedTextContent = inspectedElement.textContent.trim().replace(/\s+/g, ' ');
|
|
38
|
+
// If they have identical text contents:
|
|
39
|
+
if (inspectedTextContent === textContent) {
|
|
40
|
+
// Return a violation description.
|
|
41
|
+
return 'Heading has the same text as the prior same-level sibling heading';
|
|
42
|
+
}
|
|
43
|
+
// Otherwise, i.e. if they do not have identical text contents:
|
|
44
|
+
else {
|
|
45
|
+
// Stop inspecting.
|
|
46
|
+
break;
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
// Otherwise, i.e. if it is superior to the element:
|
|
50
|
+
else {
|
|
51
|
+
// Stop inspecting.
|
|
52
|
+
break;
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
// Otherwise, i.e. if it is not a heading:
|
|
56
|
+
else {
|
|
57
|
+
// Inspect its previous sibling.
|
|
58
|
+
inspectedElement = inspectedElement.previousElementSibling;
|
|
59
|
+
}
|
|
61
60
|
}
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
}
|
|
68
|
-
}
|
|
69
|
-
};
|
|
70
|
-
const headingLevels = [1, 2, 3, 4, 5, 6];
|
|
71
|
-
const selector = headingLevels.map(level => `body h${level}`).join(', ');
|
|
72
|
-
const whats = 'Adjacent sibling same-level headings have the same text';
|
|
73
|
-
return await doTest(
|
|
74
|
-
page, report, withItems, 'headingAmb', selector, whats, 1, getBadWhat.toString()
|
|
75
|
-
);
|
|
61
|
+
};
|
|
62
|
+
const headingLevels = [1, 2, 3, 4, 5, 6];
|
|
63
|
+
const selector = headingLevels.map(level => `body h${level}`).join(', ');
|
|
64
|
+
const whats = 'Adjacent sibling same-level headings have the same text';
|
|
65
|
+
return await (0, testaro_1.doTest)(page, report, withItems, 'headingAmb', selector, whats, 1, getBadWhat.toString());
|
|
76
66
|
};
|
|
67
|
+
exports.reporter = reporter;
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
/*
|
|
2
|
+
© 2023–2024 CVS Health and/or one of its affiliates. All rights reserved.
|
|
3
|
+
© 2026 Jeff Witt.
|
|
4
|
+
© 2026 Jonathan Robert Pool.
|
|
5
|
+
|
|
6
|
+
Licensed under the MIT License. See LICENSE file at the project root or https://opensource.org/license/mit/ for details.
|
|
7
|
+
|
|
8
|
+
SPDX-License-Identifier: MIT
|
|
9
|
+
*/
|
|
10
|
+
|
|
11
|
+
// IMPORTS
|
|
12
|
+
|
|
13
|
+
import type {Page} from 'playwright';
|
|
14
|
+
import {doTest} from '../procs/testaro';
|
|
15
|
+
import type {GetBadWhat, Report} from '../types';
|
|
16
|
+
|
|
17
|
+
// ########## FUNCTIONS
|
|
18
|
+
|
|
19
|
+
// Runs the test and returns the result.
|
|
20
|
+
export const reporter = async (page: Page, report: Report, _: unknown, withItems: boolean) => {
|
|
21
|
+
const getBadWhat: GetBadWhat = element => {
|
|
22
|
+
const {tagName} = element;
|
|
23
|
+
const level = tagName[1];
|
|
24
|
+
const textContent = element.textContent.trim().replace(/\s+/g, ' ');
|
|
25
|
+
const headingTagNames = ['H1', 'H2', 'H3', 'H4', 'H5', 'H6'];
|
|
26
|
+
// Initialize the inspected element as the previous element sibling of the element.
|
|
27
|
+
let inspectedElement = element.previousElementSibling;
|
|
28
|
+
// As long as the inspected element exists:
|
|
29
|
+
while (inspectedElement) {
|
|
30
|
+
const inspectedTagName = inspectedElement.tagName;
|
|
31
|
+
// If it is a heading:
|
|
32
|
+
if (headingTagNames.includes(inspectedTagName)) {
|
|
33
|
+
// If it is inferior to the element:
|
|
34
|
+
if (inspectedTagName[1] > level) {
|
|
35
|
+
// Stop inspecting it and start inspecting its previous sibling.
|
|
36
|
+
inspectedElement = inspectedElement.previousElementSibling;
|
|
37
|
+
continue;
|
|
38
|
+
}
|
|
39
|
+
// Otherwise, if its level is the same as that of the element:
|
|
40
|
+
else if (inspectedTagName === tagName) {
|
|
41
|
+
const inspectedTextContent = inspectedElement.textContent.trim().replace(/\s+/g, ' ');
|
|
42
|
+
// If they have identical text contents:
|
|
43
|
+
if (inspectedTextContent === textContent) {
|
|
44
|
+
// Return a violation description.
|
|
45
|
+
return 'Heading has the same text as the prior same-level sibling heading';
|
|
46
|
+
}
|
|
47
|
+
// Otherwise, i.e. if they do not have identical text contents:
|
|
48
|
+
else {
|
|
49
|
+
// Stop inspecting.
|
|
50
|
+
break;
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
// Otherwise, i.e. if it is superior to the element:
|
|
54
|
+
else {
|
|
55
|
+
// Stop inspecting.
|
|
56
|
+
break;
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
// Otherwise, i.e. if it is not a heading:
|
|
60
|
+
else {
|
|
61
|
+
// Inspect its previous sibling.
|
|
62
|
+
inspectedElement = inspectedElement.previousElementSibling;
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
};
|
|
66
|
+
const headingLevels = [1, 2, 3, 4, 5, 6];
|
|
67
|
+
const selector = headingLevels.map(level => `body h${level}`).join(', ');
|
|
68
|
+
const whats = 'Adjacent sibling same-level headings have the same text';
|
|
69
|
+
return await doTest(
|
|
70
|
+
page, report, withItems, 'headingAmb', selector, whats, 1, getBadWhat.toString()
|
|
71
|
+
);
|
|
72
|
+
};
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { Page } from 'playwright';
|
|
2
|
+
import type { Report, SeverityTotals } from '../types';
|
|
3
|
+
export declare const reporter: (page: Page, report: Report, _: unknown, withItems: boolean) => Promise<{
|
|
4
|
+
data: {
|
|
5
|
+
triggerCount: number;
|
|
6
|
+
inspectedCount: number;
|
|
7
|
+
prevented?: boolean;
|
|
8
|
+
error?: string;
|
|
9
|
+
};
|
|
10
|
+
totals: SeverityTotals;
|
|
11
|
+
standardInstances: import("../types").StandardInstance[];
|
|
12
|
+
}>;
|