ftmocks-utils 1.4.0 → 1.4.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.
- package/package.json +1 -1
- package/src/event-run-utils.js +203 -0
- package/src/index.js +2 -0
package/package.json
CHANGED
package/src/event-run-utils.js
CHANGED
|
@@ -79,6 +79,42 @@ const runEvent = async (page, event, delay = 0) => {
|
|
|
79
79
|
}
|
|
80
80
|
};
|
|
81
81
|
|
|
82
|
+
const isValidEvent = (event) => {
|
|
83
|
+
try {
|
|
84
|
+
console.log("➡ Validating event", event);
|
|
85
|
+
switch (event?.type) {
|
|
86
|
+
case "url":
|
|
87
|
+
return true;
|
|
88
|
+
case "click":
|
|
89
|
+
return true;
|
|
90
|
+
case "input":
|
|
91
|
+
return true;
|
|
92
|
+
case "keypress":
|
|
93
|
+
return true;
|
|
94
|
+
case "change":
|
|
95
|
+
return true;
|
|
96
|
+
case "dblclick":
|
|
97
|
+
return true;
|
|
98
|
+
case "contextmenu":
|
|
99
|
+
return true;
|
|
100
|
+
case "hover":
|
|
101
|
+
return true;
|
|
102
|
+
case "keydown":
|
|
103
|
+
return true;
|
|
104
|
+
case "keyup":
|
|
105
|
+
return true;
|
|
106
|
+
default:
|
|
107
|
+
return false;
|
|
108
|
+
}
|
|
109
|
+
} catch (error) {
|
|
110
|
+
console.error("Error running event", {
|
|
111
|
+
error: error.message,
|
|
112
|
+
stack: error.stack,
|
|
113
|
+
});
|
|
114
|
+
}
|
|
115
|
+
return false;
|
|
116
|
+
};
|
|
117
|
+
|
|
82
118
|
const runEvents = async (page, events, delay = 1000) => {
|
|
83
119
|
for (const event of events) {
|
|
84
120
|
await runEvent(page, event, delay);
|
|
@@ -95,6 +131,13 @@ const runEventsForTest = async (page, ftmocksConifg, testName) => {
|
|
|
95
131
|
await runEvents(page, events, ftmocksConifg.delay || 1000);
|
|
96
132
|
};
|
|
97
133
|
|
|
134
|
+
const getSelectorPosition = async (page, selector) => {
|
|
135
|
+
const element = await page.locator(selector).elementHandle();
|
|
136
|
+
const position = await element.boundingBox();
|
|
137
|
+
console.log("position", position);
|
|
138
|
+
return position;
|
|
139
|
+
};
|
|
140
|
+
|
|
98
141
|
const runEventsInPresentationMode = async (page, ftmocksConifg, testName) => {
|
|
99
142
|
let currentEventIndex = 1;
|
|
100
143
|
const eventsFile = path.join(
|
|
@@ -132,9 +175,169 @@ const runEventsInPresentationMode = async (page, ftmocksConifg, testName) => {
|
|
|
132
175
|
await runEvent(page, events[0]);
|
|
133
176
|
};
|
|
134
177
|
|
|
178
|
+
const runEventsInTrainingMode = async (page, ftmocksConifg, testName) => {
|
|
179
|
+
let currentEventIndex = 0;
|
|
180
|
+
const eventsFile = path.join(
|
|
181
|
+
getMockDir(ftmocksConifg),
|
|
182
|
+
`test_${nameToFolder(testName)}`,
|
|
183
|
+
`_events.json`
|
|
184
|
+
);
|
|
185
|
+
const events = JSON.parse(fs.readFileSync(eventsFile, "utf8"));
|
|
186
|
+
|
|
187
|
+
// Expose Node function
|
|
188
|
+
await page.exposeFunction("getNextEvent", async () => {
|
|
189
|
+
let result = false;
|
|
190
|
+
while (!result) {
|
|
191
|
+
currentEventIndex = currentEventIndex + 1;
|
|
192
|
+
if (currentEventIndex === events.length) {
|
|
193
|
+
console.log("➡ No more events to validate!");
|
|
194
|
+
return;
|
|
195
|
+
}
|
|
196
|
+
result = isValidEvent(events[currentEventIndex]);
|
|
197
|
+
}
|
|
198
|
+
if (events[currentEventIndex]) {
|
|
199
|
+
const selector = await getLocator(page, events[currentEventIndex]);
|
|
200
|
+
const position = await getSelectorPosition(page, selector);
|
|
201
|
+
const element = await page.locator(selector).elementHandle();
|
|
202
|
+
return {
|
|
203
|
+
event: events[currentEventIndex],
|
|
204
|
+
selector,
|
|
205
|
+
position,
|
|
206
|
+
element,
|
|
207
|
+
};
|
|
208
|
+
}
|
|
209
|
+
return null;
|
|
210
|
+
});
|
|
211
|
+
|
|
212
|
+
// Inject keyboard listener into browser
|
|
213
|
+
await page.addInitScript(async () => {
|
|
214
|
+
let currentEventInfo = null;
|
|
215
|
+
// Create and style the popover
|
|
216
|
+
const popover = document.createElement("div");
|
|
217
|
+
popover.id = "ftmocks-popover-training-mode";
|
|
218
|
+
popover.style.position = "absolute";
|
|
219
|
+
popover.style.top = "0";
|
|
220
|
+
popover.style.left = "0";
|
|
221
|
+
popover.style.minWidth = "100px";
|
|
222
|
+
popover.style.height = "58px";
|
|
223
|
+
popover.style.background = "rgba(40,40,40,0.97)";
|
|
224
|
+
popover.style.color = "#fff";
|
|
225
|
+
popover.style.display = "none";
|
|
226
|
+
popover.style.zIndex = "99999";
|
|
227
|
+
popover.style.fontFamily = "sans-serif";
|
|
228
|
+
popover.style.fontSize = "16px";
|
|
229
|
+
popover.style.textAlign = "center";
|
|
230
|
+
popover.style.lineHeight = "1.5";
|
|
231
|
+
popover.style.padding = "16px 24px";
|
|
232
|
+
popover.style.borderRadius = "8px";
|
|
233
|
+
popover.style.boxShadow = "0 2px 12px rgba(0,0,0,0.25)";
|
|
234
|
+
|
|
235
|
+
function showPopover(message, position = { x: 0, y: 0 }) {
|
|
236
|
+
if (!document.getElementById("ftmocks-popover-training-mode")) {
|
|
237
|
+
document.body.appendChild(popover);
|
|
238
|
+
}
|
|
239
|
+
popover.textContent = message;
|
|
240
|
+
popover.style.display = "block";
|
|
241
|
+
popover.style.left = position.x + position.width / 2 + "px";
|
|
242
|
+
popover.style.top = position.y + position.height + "px";
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
function hidePopover() {
|
|
246
|
+
popover.style.display = "none";
|
|
247
|
+
}
|
|
248
|
+
|
|
249
|
+
const initialEventRun = async () => {
|
|
250
|
+
currentEventInfo = await window.getNextEvent();
|
|
251
|
+
if (currentEventInfo) {
|
|
252
|
+
showPopover(currentEventInfo.event.type, currentEventInfo.position);
|
|
253
|
+
}
|
|
254
|
+
};
|
|
255
|
+
|
|
256
|
+
window.addEventListener("click", async (event) => {
|
|
257
|
+
if (
|
|
258
|
+
currentEventInfo?.type === "click" &&
|
|
259
|
+
event.target.isEqualNode(currentEventInfo?.element) &&
|
|
260
|
+
currentEventInfo?.element?.contains(event.target)
|
|
261
|
+
) {
|
|
262
|
+
currentEventInfo = await window.getNextEvent();
|
|
263
|
+
if (currentEventInfo) {
|
|
264
|
+
showPopover(currentEventInfo.event.type, currentEventInfo.position);
|
|
265
|
+
} else {
|
|
266
|
+
hidePopover();
|
|
267
|
+
}
|
|
268
|
+
} else {
|
|
269
|
+
initialEventRun();
|
|
270
|
+
}
|
|
271
|
+
});
|
|
272
|
+
window.addEventListener("dblclick", async (event) => {
|
|
273
|
+
if (
|
|
274
|
+
currentEventInfo?.type === "dblclick" &&
|
|
275
|
+
event.target.isEqualNode(currentEventInfo?.element) &&
|
|
276
|
+
currentEventInfo?.element?.contains(event.target)
|
|
277
|
+
) {
|
|
278
|
+
currentEventInfo = await window.getNextEvent();
|
|
279
|
+
if (currentEventInfo) {
|
|
280
|
+
showPopover(currentEventInfo.event.type, currentEventInfo.position);
|
|
281
|
+
} else {
|
|
282
|
+
hidePopover();
|
|
283
|
+
}
|
|
284
|
+
} else {
|
|
285
|
+
initialEventRun();
|
|
286
|
+
}
|
|
287
|
+
});
|
|
288
|
+
window.addEventListener("contextmenu", async (event) => {
|
|
289
|
+
if (
|
|
290
|
+
currentEventInfo?.type === "contextmenu" &&
|
|
291
|
+
event.target.isEqualNode(currentEventInfo?.element) &&
|
|
292
|
+
currentEventInfo?.element?.contains(event.target)
|
|
293
|
+
) {
|
|
294
|
+
currentEventInfo = await window.getNextEvent();
|
|
295
|
+
if (currentEventInfo) {
|
|
296
|
+
showPopover(currentEventInfo.event.type, currentEventInfo.position);
|
|
297
|
+
} else {
|
|
298
|
+
hidePopover();
|
|
299
|
+
}
|
|
300
|
+
} else {
|
|
301
|
+
initialEventRun();
|
|
302
|
+
}
|
|
303
|
+
});
|
|
304
|
+
window.addEventListener("input", async (event) => {
|
|
305
|
+
if (
|
|
306
|
+
currentEventInfo?.type === "input" &&
|
|
307
|
+
event.target.isEqualNode(currentEventInfo?.element) &&
|
|
308
|
+
currentEventInfo?.element?.contains(event.target)
|
|
309
|
+
) {
|
|
310
|
+
currentEventInfo = await window.getNextEvent();
|
|
311
|
+
if (currentEventInfo) {
|
|
312
|
+
showPopover(currentEventInfo.event.type, currentEventInfo.position);
|
|
313
|
+
}
|
|
314
|
+
} else {
|
|
315
|
+
initialEventRun();
|
|
316
|
+
}
|
|
317
|
+
});
|
|
318
|
+
window.addEventListener("keypress", async (event) => {
|
|
319
|
+
if (
|
|
320
|
+
currentEventInfo?.type === "keypress" &&
|
|
321
|
+
event.target.isEqualNode(currentEventInfo?.element) &&
|
|
322
|
+
currentEventInfo?.element?.contains(event.target)
|
|
323
|
+
) {
|
|
324
|
+
currentEventInfo = await window.getNextEvent();
|
|
325
|
+
if (currentEventInfo) {
|
|
326
|
+
showPopover(currentEventInfo.event.type, currentEventInfo.position);
|
|
327
|
+
}
|
|
328
|
+
} else {
|
|
329
|
+
initialEventRun();
|
|
330
|
+
}
|
|
331
|
+
});
|
|
332
|
+
});
|
|
333
|
+
|
|
334
|
+
await runEvent(page, events[0]);
|
|
335
|
+
};
|
|
336
|
+
|
|
135
337
|
module.exports = {
|
|
136
338
|
runEvents,
|
|
137
339
|
runEventsForTest,
|
|
138
340
|
runEventsInPresentationMode,
|
|
341
|
+
runEventsInTrainingMode,
|
|
139
342
|
runEvent,
|
|
140
343
|
};
|
package/src/index.js
CHANGED
|
@@ -26,6 +26,7 @@ const {
|
|
|
26
26
|
runEventsForTest,
|
|
27
27
|
runEvent,
|
|
28
28
|
runEventsInPresentationMode,
|
|
29
|
+
runEventsInTrainingMode,
|
|
29
30
|
} = require("./event-run-utils");
|
|
30
31
|
|
|
31
32
|
// Export functions as a module
|
|
@@ -52,4 +53,5 @@ module.exports = {
|
|
|
52
53
|
runEventsForTest,
|
|
53
54
|
runEvent,
|
|
54
55
|
runEventsInPresentationMode,
|
|
56
|
+
runEventsInTrainingMode,
|
|
55
57
|
};
|