testaro 25.0.1 → 25.1.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/package.json +1 -1
- package/testaro/hover.js +48 -143
package/package.json
CHANGED
package/testaro/hover.js
CHANGED
|
@@ -1,153 +1,58 @@
|
|
|
1
1
|
/*
|
|
2
2
|
hover
|
|
3
|
-
This test reports unexpected impacts of hovering
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
elements
|
|
8
|
-
'onmouseenter' or 'onmouseover' attributes.
|
|
9
|
-
|
|
10
|
-
Despite the delay, the test can make the execution time practical by randomly sampling triggers
|
|
11
|
-
instead of hovering over all of them. When sampling is performed, the results may vary from one
|
|
12
|
-
execution to another. Because hover impacts typically occur near the beginning of a page with
|
|
13
|
-
navigation menus, the probability of the inclusion of a trigger in a sample decreases with the
|
|
14
|
-
index of the trigger.
|
|
15
|
-
|
|
16
|
-
Pixel changes: If no pixel changes occur immediately after an element is hovered over, the page
|
|
17
|
-
is examined once more, after 0.5 second. The greater the fraction of changed pixels, the greater
|
|
18
|
-
the ordinal severity.
|
|
19
|
-
|
|
20
|
-
Unhoverability: An element is reported as unhoverable when it fails the Playwright actionability
|
|
21
|
-
checks for hovering, i.e. fails to be attached to the DOM, visible, stable (not or no longer
|
|
22
|
-
animating), and able to receive events. All triggers satisfy the first two conditions, so only the
|
|
23
|
-
last two might fail. Playwright defines the ability to receive events as being the target of an
|
|
24
|
-
action on the location where the center of the element is, rather than some other element with a
|
|
25
|
-
higher zIndex value in the same location being the target.
|
|
26
|
-
|
|
27
|
-
WARNING: This test uses the procs/visChange module. See the warning in that module about browser
|
|
28
|
-
types.
|
|
3
|
+
This test reports unexpected impacts of hovering. The elements that are subjected to hovering
|
|
4
|
+
(called “triggers”) include all the elements that have aria-controls, aria-expanded,
|
|
5
|
+
onmouseenter, or onmouseover' attributes and a sample of all visible elements in the body. If
|
|
6
|
+
hovering over an element results in an increase or decrease in the total count of visible
|
|
7
|
+
elements in the body, the rule is considered violated.
|
|
29
8
|
*/
|
|
30
9
|
|
|
31
|
-
// IMPORTS
|
|
32
|
-
|
|
33
|
-
// Module to
|
|
34
|
-
const {
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
//
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
const
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
const locsAll = await locAll.all();
|
|
53
|
-
// Get the population-to-sample ratio.
|
|
54
|
-
const psRatio = Math.max(1, locsAll.length / sampleSize);
|
|
55
|
-
// Get a sample of the triggers.
|
|
56
|
-
const sampleIndexes = getSample(locsAll, sampleSize);
|
|
57
|
-
const sample = sampleIndexes.map(index => locsAll[index]);
|
|
58
|
-
// For each trigger in the sample:
|
|
59
|
-
for (const loc of sample) {
|
|
60
|
-
// Hover over it and get the fractional pixel change.
|
|
61
|
-
const hoverData = await visChange(page, {
|
|
62
|
-
delayBefore: 0,
|
|
63
|
-
delayBetween: 500,
|
|
64
|
-
exclusion: loc
|
|
65
|
-
});
|
|
66
|
-
// If the hovering and measurement succeeded:
|
|
67
|
-
if (hoverData.success) {
|
|
68
|
-
// If any pixels changed:
|
|
69
|
-
if (hoverData.changePercent) {
|
|
70
|
-
// Get the ordinal severity from the fractional pixel change.
|
|
71
|
-
const ordinalSeverity = Math.floor(Math.min(3, 0.4 * Math.sqrt(hoverData.changePercent)));
|
|
72
|
-
// Add to the totals.
|
|
73
|
-
totals[ordinalSeverity] += psRatio;
|
|
74
|
-
// If itemization is required:
|
|
75
|
-
if (withItems) {
|
|
76
|
-
// Get data on the trigger.
|
|
77
|
-
const elData = await getLocatorData(loc);
|
|
78
|
-
// Add an instance to the result.
|
|
79
|
-
standardInstances.push({
|
|
80
|
-
ruleID: 'hover',
|
|
81
|
-
what: 'Hovering over the element changes the page',
|
|
82
|
-
ordinalSeverity,
|
|
83
|
-
tagName: elData.tagName,
|
|
84
|
-
id: elData.id,
|
|
85
|
-
location: elData.location,
|
|
86
|
-
excerpt: elData.excerpt
|
|
87
|
-
});
|
|
88
|
-
}
|
|
89
|
-
}
|
|
90
|
-
}
|
|
91
|
-
// Otherwise, i.e. if hovering and measurement failed:
|
|
92
|
-
else {
|
|
93
|
-
// Add to the totals.
|
|
94
|
-
totals[3] += psRatio;
|
|
95
|
-
// If itemization is required:
|
|
96
|
-
if (withItems) {
|
|
97
|
-
// Get data on the trigger.
|
|
98
|
-
const elData = await getLocatorData(loc);
|
|
99
|
-
// Add an instance to the result.
|
|
100
|
-
standardInstances.push({
|
|
101
|
-
ruleID: 'hover',
|
|
102
|
-
what: 'Element is not hoverable',
|
|
103
|
-
ordinalSeverity: 3,
|
|
104
|
-
tagName: elData.tagName,
|
|
105
|
-
id: elData.id,
|
|
106
|
-
location: elData.location,
|
|
107
|
-
excerpt: elData.excerpt
|
|
108
|
-
});
|
|
109
|
-
}
|
|
110
|
-
}
|
|
111
|
-
// Reload the page to preserve locator integrity.
|
|
10
|
+
// ########## IMPORTS
|
|
11
|
+
|
|
12
|
+
// Module to perform common operations.
|
|
13
|
+
const {init, report} = require('../procs/testaro');
|
|
14
|
+
|
|
15
|
+
// ########## FUNCTIONS
|
|
16
|
+
|
|
17
|
+
// Runs the test and returns the result.
|
|
18
|
+
exports.reporter = async (page, withItems) => {
|
|
19
|
+
// Initialize the locators and result.
|
|
20
|
+
const all = await init(
|
|
21
|
+
page, 'body [aria-controls], body [aria-expanded], body [onmouseenter], body [onmouseover]'
|
|
22
|
+
);
|
|
23
|
+
const miscAll = await init(page, 'body *:visible');
|
|
24
|
+
all.allLocs.push(... miscAll.allLocs.slice(0, - all.allLocs.length));
|
|
25
|
+
// For each locator:
|
|
26
|
+
for (const loc of all.allLocs) {
|
|
27
|
+
// Get how many elements are added or subtracted when the element is hovered over.
|
|
28
|
+
await page.mouse.move(0, 0);
|
|
29
|
+
const loc0 = page.locator('body *:visible');
|
|
30
|
+
const elementCount0 = await loc0.count();
|
|
112
31
|
try {
|
|
113
|
-
await
|
|
32
|
+
await loc.hover({
|
|
33
|
+
force: true,
|
|
34
|
+
timeout: 100
|
|
35
|
+
});
|
|
36
|
+
const loc1 = page.locator('body *:visible');
|
|
37
|
+
const elementCount1 = await loc1.count();
|
|
38
|
+
const additions = elementCount1 - elementCount0;
|
|
39
|
+
// If any elements are:
|
|
40
|
+
if (additions !== 0) {
|
|
41
|
+
// Add the locator and the change of element count to the array of violators.
|
|
42
|
+
const impact = additions > 0
|
|
43
|
+
? `added ${additions} elements to the page`
|
|
44
|
+
: `subtracted ${- additions} from the page`;
|
|
45
|
+
all.locs.push([loc, impact]);
|
|
46
|
+
}
|
|
114
47
|
}
|
|
115
48
|
catch(error) {
|
|
116
|
-
console.log(
|
|
117
|
-
}
|
|
118
|
-
}
|
|
119
|
-
// If itemization is not required:
|
|
120
|
-
if (! withItems) {
|
|
121
|
-
// For each ordinal severity:
|
|
122
|
-
for (const index in totals) {
|
|
123
|
-
// If there were any instances with it:
|
|
124
|
-
if (totals[index]) {
|
|
125
|
-
// Add a summary instance to the result.
|
|
126
|
-
standardInstances.push({
|
|
127
|
-
ruleID: 'hover',
|
|
128
|
-
what: 'Hovering over elements changes the page or fails',
|
|
129
|
-
ordinalSeverity: index,
|
|
130
|
-
count: Math.round(totals[index]),
|
|
131
|
-
tagName: '',
|
|
132
|
-
id: '',
|
|
133
|
-
location: {
|
|
134
|
-
doc: '',
|
|
135
|
-
type: '',
|
|
136
|
-
spec: ''
|
|
137
|
-
},
|
|
138
|
-
excerpt: ''
|
|
139
|
-
});
|
|
140
|
-
}
|
|
49
|
+
console.log(`Hovering timed out (${error.message.replace(/[\n].+/s, '')})`);
|
|
141
50
|
}
|
|
142
51
|
}
|
|
143
|
-
//
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
return
|
|
149
|
-
data,
|
|
150
|
-
totals,
|
|
151
|
-
standardInstances
|
|
152
|
-
};
|
|
52
|
+
// Populate and return the result.
|
|
53
|
+
const whats = [
|
|
54
|
+
'Hovering over the element __param__',
|
|
55
|
+
'Hovering over elements adds elements to or subtracts elements from the page'
|
|
56
|
+
];
|
|
57
|
+
return await report(withItems, all, 'hover', whats, 0);
|
|
153
58
|
};
|