@lvce-editor/test-with-playwright-worker 22.36.2 → 22.36.3

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.
Files changed (2) hide show
  1. package/dist/workerMain.js +172 -6
  2. package/package.json +1 -1
@@ -1198,6 +1198,162 @@ const get = id => {
1198
1198
  return rpcs[id];
1199
1199
  };
1200
1200
 
1201
+ // This function is serialized by Playwright and must not close over module bindings.
1202
+ const install = () => {
1203
+ const limit = 5000;
1204
+ const payloadLimit = 8192;
1205
+ const entries = [];
1206
+ let sequence = 0;
1207
+ const channels = new WeakMap();
1208
+ let nextChannel = 0;
1209
+ const originalAdd = Object.getOwnPropertyDescriptor(EventTarget.prototype, 'addEventListener').value;
1210
+ const record = (kind, data) => {
1211
+ const entry = {
1212
+ ...data,
1213
+ kind,
1214
+ sequence: sequence++,
1215
+ timestamp: performance.now()
1216
+ };
1217
+ entries[entry.sequence % limit] = entry;
1218
+ };
1219
+ const describe = target => {
1220
+ if (!(target instanceof Element)) {
1221
+ if (!(target instanceof Node)) return 'unknown';
1222
+ return `${target.nodeName}:${target.nodeValue || ''}`.slice(0, 200);
1223
+ }
1224
+ return `${target.tagName}#${target.id}.${target.getAttribute('class') || ''}`.slice(0, 200);
1225
+ };
1226
+ const serialize = value => {
1227
+ let truncated = false;
1228
+ const seen = new WeakSet();
1229
+ try {
1230
+ const text = JSON.stringify(value, (_key, item) => {
1231
+ if (typeof item === 'bigint') return `${item}n`;
1232
+ if (typeof item === 'string') {
1233
+ truncated ||= item.length > 2048;
1234
+ return item.slice(0, 2048);
1235
+ }
1236
+ if (typeof item !== 'object' || item === null) return item;
1237
+ if (seen.has(item)) return '[Circular]';
1238
+ seen.add(item);
1239
+ if (item instanceof MessagePort) return '[MessagePort]';
1240
+ if (item instanceof ArrayBuffer) return `[ArrayBuffer ${item.byteLength}]`;
1241
+ if (ArrayBuffer.isView(item)) return `[${item.constructor.name} ${item.byteLength}]`;
1242
+ return item;
1243
+ }) || '';
1244
+ return {
1245
+ payload: text.slice(0, payloadLimit),
1246
+ truncated: truncated || text.length > payloadLimit
1247
+ };
1248
+ } catch {
1249
+ return {
1250
+ payload: '[Unserializable]',
1251
+ truncated: true
1252
+ };
1253
+ }
1254
+ };
1255
+ const observe = target => {
1256
+ const existing = channels.get(target);
1257
+ if (existing !== undefined) return existing;
1258
+ const channel = nextChannel++;
1259
+ channels.set(target, channel);
1260
+ Reflect.apply(originalAdd, target, ['message', event => {
1261
+ record('rpc-received', {
1262
+ channel,
1263
+ ...serialize(event.data)
1264
+ });
1265
+ }]);
1266
+ return channel;
1267
+ };
1268
+ class EventHooks {
1269
+ addEventListener(...args) {
1270
+ if (args[0] === 'message' && (this instanceof MessagePort || this instanceof Worker)) observe(this);
1271
+ return Reflect.apply(originalAdd, this, args);
1272
+ }
1273
+ }
1274
+ Object.defineProperty(EventTarget.prototype, 'addEventListener', {
1275
+ ...Object.getOwnPropertyDescriptor(EventTarget.prototype, 'addEventListener'),
1276
+ value: Object.getOwnPropertyDescriptor(EventHooks.prototype, 'addEventListener').value
1277
+ });
1278
+ for (const prototype of [MessagePort.prototype, Worker.prototype]) {
1279
+ const postDescriptor = Object.getOwnPropertyDescriptor(prototype, 'postMessage');
1280
+ const descriptor = Object.getOwnPropertyDescriptor(prototype, 'onmessage');
1281
+ const originalSet = Object.getOwnPropertyDescriptor(descriptor, 'set').value;
1282
+ class PortHooks {
1283
+ postMessage(...args) {
1284
+ const channel = observe(this);
1285
+ const data = serialize(args[0]);
1286
+ const result = Reflect.apply(postDescriptor.value, this, args);
1287
+ record('rpc-sent', {
1288
+ channel,
1289
+ ...data
1290
+ });
1291
+ return result;
1292
+ }
1293
+ set onmessage(listener) {
1294
+ observe(this);
1295
+ Reflect.apply(originalSet, this, [listener]);
1296
+ }
1297
+ }
1298
+ const hookDescriptor = Object.getOwnPropertyDescriptor(PortHooks.prototype, 'onmessage');
1299
+ Object.defineProperties(prototype, {
1300
+ onmessage: {
1301
+ ...descriptor,
1302
+ set: Object.getOwnPropertyDescriptor(hookDescriptor, 'set').value
1303
+ },
1304
+ postMessage: {
1305
+ ...postDescriptor,
1306
+ value: Object.getOwnPropertyDescriptor(PortHooks.prototype, 'postMessage').value
1307
+ }
1308
+ });
1309
+ }
1310
+ for (const type of ['click', 'input', 'keydown', 'keyup', 'pointerdown', 'pointerup', 'pointerover', 'pointerout', 'focusin', 'focusout']) {
1311
+ document.addEventListener(type, event => {
1312
+ record('input', {
1313
+ event: type,
1314
+ key: event.key,
1315
+ target: describe(event.target),
1316
+ trusted: event.isTrusted
1317
+ });
1318
+ }, {
1319
+ capture: true,
1320
+ passive: true
1321
+ });
1322
+ }
1323
+ const observer = new MutationObserver(mutations => {
1324
+ record('dom-mutation', {
1325
+ changes: mutations.slice(0, 10).map(mutation => ({
1326
+ added: [...mutation.addedNodes].slice(0, 2).map(describe),
1327
+ addedCount: mutation.addedNodes.length,
1328
+ attribute: mutation.attributeName,
1329
+ removed: [...mutation.removedNodes].slice(0, 2).map(describe),
1330
+ removedCount: mutation.removedNodes.length,
1331
+ target: describe(mutation.target),
1332
+ type: mutation.type,
1333
+ value: mutation.attributeName && mutation.target instanceof Element ? mutation.target.getAttribute(mutation.attributeName)?.slice(0, 200) : undefined
1334
+ })),
1335
+ count: mutations.length
1336
+ });
1337
+ });
1338
+ observer.observe(document, {
1339
+ attributes: true,
1340
+ characterData: true,
1341
+ childList: true,
1342
+ subtree: true
1343
+ });
1344
+ Object.defineProperty(globalThis, '__lvceTraceTimeline', {
1345
+ value: () => {
1346
+ const offset = sequence > limit ? sequence % limit : 0;
1347
+ return {
1348
+ dropped: Math.max(0, sequence - limit),
1349
+ entries: [...entries.slice(offset), ...entries.slice(0, offset)],
1350
+ limit,
1351
+ version: 1
1352
+ };
1353
+ }
1354
+ });
1355
+ };
1356
+
1201
1357
  const HandleResult = 'HandleResult';
1202
1358
  const HandleFinalResult = 'HandleFinalResult';
1203
1359
 
@@ -1268,19 +1424,26 @@ const exportTrace = async ({
1268
1424
  page,
1269
1425
  test
1270
1426
  }) => {
1271
- let text;
1427
+ let capture;
1272
1428
  try {
1273
- text = await page.evaluate(traceSelector => {
1274
- return globalThis.document.querySelector(traceSelector)?.textContent || undefined;
1429
+ capture = await page.evaluate(traceSelector => {
1430
+ return {
1431
+ text: globalThis.document.querySelector(traceSelector)?.textContent || undefined,
1432
+ timeline: globalThis.__lvceTraceTimeline?.()
1433
+ };
1275
1434
  }, selector);
1276
1435
  } catch {
1277
1436
  return false;
1278
1437
  }
1279
- if (!text) {
1438
+ if (!capture.text && !capture.timeline) {
1280
1439
  return false;
1281
1440
  }
1282
- JSON.parse(text);
1283
- await writeFile(join(directory, getFileName(test)), `${text}\n`);
1441
+ const trace = capture.text ? JSON.parse(capture.text) : {
1442
+ entries: [],
1443
+ version: 1
1444
+ };
1445
+ if (capture.timeline) trace.timeline = capture.timeline;
1446
+ await writeFile(join(directory, getFileName(test)), `${JSON.stringify(trace)}\n`);
1284
1447
  return true;
1285
1448
  };
1286
1449
 
@@ -2472,6 +2635,9 @@ const runAllTests = async (extensionPath, testPath, cwd, browser, headless, time
2472
2635
  testPath
2473
2636
  });
2474
2637
  try {
2638
+ if (traceRendererWorker) {
2639
+ await page.addInitScript(install);
2640
+ }
2475
2641
  if (reusePage) {
2476
2642
  await runWithJavascriptCoverage({
2477
2643
  coverage,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lvce-editor/test-with-playwright-worker",
3
- "version": "22.36.2",
3
+ "version": "22.36.3",
4
4
  "description": "Worker package for test-with-playwright",
5
5
  "repository": {
6
6
  "type": "git",