testaro 4.10.4 → 4.11.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/commands.js CHANGED
@@ -153,7 +153,7 @@ exports.commands = {
153
153
  axe: [
154
154
  'Perform an Axe test',
155
155
  {
156
- withItems: [true, 'boolean'],
156
+ detailLevel: [true, 'number', '', 'count to include of: violations, incomplete, passes, inapplicable'],
157
157
  rules: [true, 'array', 'areStrings', 'rule names, or empty if all']
158
158
  }
159
159
  ],
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "testaro",
3
- "version": "4.10.4",
3
+ "version": "4.11.0",
4
4
  "description": "Automation of accessibility testing",
5
5
  "main": "index.js",
6
6
  "scripts": {
package/tests/axe.js CHANGED
@@ -3,13 +3,26 @@
3
3
  This test implements the axe-core ruleset for accessibility.
4
4
 
5
5
  The rules argument defaults to all rules; otherwise, specify an array of rule names.
6
- Experimental, needs-review, and best-practice rules are ignored.
6
+
7
+ The detailLevel argument specifies how many result categories are to be included in the
8
+ details. 0 = none; 1 = violations; 2 = violations and incomplete; 3 = violations, incomplete,
9
+ and passes; 4 = violations, incomplete, passes, and inapplicable. Regardless of the value of this
10
+ argument, Axe-core is instructed to report all nodes with violation or incomplete results, but only
11
+ 1 node per rule found to be passed or inapplicable. Therefore, from the results of this test it
12
+ is possible to count the rules passed and the inapplicable rules, but not the nodes for which each
13
+ rule is passed or inapplicable. To count those nodes, one would need to revise the 'resultTypes'
14
+ property of the 'axeOptions' object.
15
+
16
+ The report of this test shows rule totals by result category and, within the violation and
17
+ incomplete categories, node totals by severity. It does not show rule or node totals by test
18
+ category (“tag”), such as 'wcag21aaa'. Scoring can consider test categories by getting the value
19
+ of the 'tags' property of each rule.
7
20
  */
8
21
  // IMPORTS
9
- const {injectAxe, getViolations} = require('axe-playwright');
22
+ const {injectAxe, getAxeResults} = require('axe-playwright');
10
23
  // FUNCTIONS
11
24
  // Conducts and reports an Axe test.
12
- exports.reporter = async (page, withItems, rules = []) => {
25
+ exports.reporter = async (page, detailLevel, rules = []) => {
13
26
  // Initialize the report.
14
27
  const data = {};
15
28
  // Inject axe-core into the page.
@@ -22,81 +35,65 @@ exports.reporter = async (page, withItems, rules = []) => {
22
35
  // If the injection succeeded:
23
36
  if (! data.prevented) {
24
37
  // Get the data on the elements violating the specified axe-core rules.
25
- const axeOptions = {};
38
+ const axeOptions = {
39
+ resultTypes: ['violations', 'incomplete']
40
+ };
26
41
  if (rules.length) {
27
42
  axeOptions.runOnly = rules;
28
43
  }
29
- const axeReport = await getViolations(page, null, axeOptions)
44
+ else {
45
+ axeOptions.runOnly = ['experimental', 'best-practice', 'wcag2a', 'wcag2aa', 'wcag2aaa', 'wcag21a', 'wcag21aa', 'wcag21aaa'];
46
+ }
47
+ const axeReport = await getAxeResults(page, null, axeOptions)
30
48
  .catch(error => {
31
49
  console.log(`ERROR: Axe failed (${error.message}'`);
32
50
  return '';
33
51
  });
34
52
  // If the test succeeded:
35
- if (Array.isArray(axeReport)) {
36
- // Initialize a report.
37
- data.warnings = 0;
38
- data.violations = {
39
- minor: 0,
40
- moderate: 0,
41
- serious: 0,
42
- critical: 0
53
+ const {inapplicable, passes, incomplete, violations} = axeReport;
54
+ if (violations) {
55
+ // Initialize the result.
56
+ data.totals = {
57
+ rulesNA: 0,
58
+ rulesPassed: 0,
59
+ rulesWarned: 0,
60
+ rulesViolated: 0,
61
+ warnings: {
62
+ minor: 0,
63
+ moderate: 0,
64
+ serious: 0,
65
+ critical: 0
66
+ },
67
+ violations: {
68
+ minor: 0,
69
+ moderate: 0,
70
+ serious: 0,
71
+ critical: 0
72
+ }
43
73
  };
44
- if (withItems) {
45
- data.items = [];
46
- }
47
- // If there were any violations:
48
- if (axeReport.length) {
49
- // FUNCTION DEFINITIONS START
50
- // Compacts a check violation.
51
- const compactCheck = checkObj => {
52
- return {
53
- check: checkObj.id,
54
- description: checkObj.message,
55
- impact: checkObj.impact
56
- };
57
- };
58
- // Compacts a violating element.
59
- const compactViolator = elObj => {
60
- const out = {
61
- selector: elObj.target[0],
62
- impact: elObj.impact
63
- };
64
- if (elObj.any && elObj.any.length) {
65
- out['must pass any of'] = elObj.any.map(checkObj => compactCheck(checkObj));
66
- }
67
- if (elObj.none && elObj.none.length) {
68
- out['must pass all of'] = elObj.none.map(checkObj => compactCheck(checkObj));
69
- }
70
- return out;
71
- };
72
- // Compacts a violated rule.
73
- const compactRule = rule => {
74
- const out = {
75
- rule: rule.id,
76
- description: rule.description,
77
- impact: rule.impact,
78
- elements: {}
79
- };
80
- if (rule.nodes && rule.nodes.length) {
81
- out.elements = rule.nodes.map(el => compactViolator(el));
82
- }
83
- return out;
84
- };
85
- // FUNCTION DEFINITIONS END
86
- // For each rule violated:
87
- axeReport.forEach(rule => {
88
- // For each element violating the rule:
89
- rule.nodes.forEach(element => {
90
- // Increment the element count of the impact of its violation.
91
- data.violations[element.impact]++;
92
- });
93
- // If details are required:
94
- if (withItems) {
95
- // Add it to the report.
96
- data.items.push(compactRule(rule));
97
- }
74
+ data.details = axeReport;
75
+ // Populate the totals.
76
+ const {totals} = data;
77
+ totals.rulesNA = inapplicable.length;
78
+ totals.rulesPassed = passes.length;
79
+ incomplete.forEach(rule => {
80
+ totals.rulesWarned++;
81
+ rule.nodes.forEach(node => {
82
+ totals.warnings[node.impact]++;
83
+ });
84
+ });
85
+ violations.forEach(rule => {
86
+ totals.rulesViolated++;
87
+ rule.nodes.forEach(node => {
88
+ totals.violations[node.impact]++;
98
89
  });
99
- }
90
+ });
91
+ // Delete irrelevant properties from the report details.
92
+ const irrelevants = ['inapplicable', 'passes', 'incomplete', 'violations']
93
+ .slice(0, 4 - detailLevel);
94
+ irrelevants.forEach(irrelevant => {
95
+ delete axeReport[irrelevant];
96
+ });
100
97
  }
101
98
  // Otherwise, i.e. if the test failed:
102
99
  else {