@ricsam/isolate-runtime 0.1.14 → 0.1.16
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/README.md +88 -24
- package/dist/cjs/index.cjs +406 -76
- package/dist/cjs/index.cjs.map +3 -3
- package/dist/cjs/package.json +1 -1
- package/dist/mjs/index.mjs +412 -62
- package/dist/mjs/index.mjs.map +3 -3
- package/dist/mjs/package.json +1 -1
- package/dist/types/index.d.ts +45 -5
- package/package.json +1 -1
- package/dist/cjs/internal.cjs +0 -95
- package/dist/cjs/internal.cjs.map +0 -10
- package/dist/mjs/internal.mjs +0 -52
- package/dist/mjs/internal.mjs.map +0 -10
- package/dist/types/internal.d.ts +0 -39
package/dist/cjs/index.cjs
CHANGED
|
@@ -4,23 +4,6 @@ var __defProp = Object.defineProperty;
|
|
|
4
4
|
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
5
5
|
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
6
6
|
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
7
|
-
var __reExport = (target, mod, secondTarget) => {
|
|
8
|
-
for (let key of __getOwnPropNames(mod))
|
|
9
|
-
if (!__hasOwnProp.call(target, key) && key !== "default")
|
|
10
|
-
__defProp(target, key, {
|
|
11
|
-
get: () => mod[key],
|
|
12
|
-
enumerable: true
|
|
13
|
-
});
|
|
14
|
-
if (secondTarget) {
|
|
15
|
-
for (let key of __getOwnPropNames(mod))
|
|
16
|
-
if (!__hasOwnProp.call(secondTarget, key) && key !== "default")
|
|
17
|
-
__defProp(secondTarget, key, {
|
|
18
|
-
get: () => mod[key],
|
|
19
|
-
enumerable: true
|
|
20
|
-
});
|
|
21
|
-
return secondTarget;
|
|
22
|
-
}
|
|
23
|
-
};
|
|
24
7
|
var __toESM = (mod, isNodeMode, target) => {
|
|
25
8
|
target = mod != null ? __create(__getProtoOf(mod)) : {};
|
|
26
9
|
const to = isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target;
|
|
@@ -74,6 +57,8 @@ __export(exports_src, {
|
|
|
74
57
|
normalizeEntryFilename: () => import_isolate_protocol2.normalizeEntryFilename,
|
|
75
58
|
hasTests: () => import_isolate_test_environment2.hasTests,
|
|
76
59
|
getTestCount: () => import_isolate_test_environment2.getTestCount,
|
|
60
|
+
getDefaultPlaywrightHandlerMetadata: () => import_isolate_playwright2.getDefaultPlaywrightHandlerMetadata,
|
|
61
|
+
defaultPlaywrightHandler: () => import_isolate_playwright2.defaultPlaywrightHandler,
|
|
77
62
|
createRuntime: () => createRuntime,
|
|
78
63
|
createPlaywrightHandler: () => import_isolate_playwright2.createPlaywrightHandler,
|
|
79
64
|
createNodeFileSystemHandler: () => import_isolate_fs2.createNodeFileSystemHandler
|
|
@@ -106,7 +91,6 @@ var import_isolate_path2 = require("@ricsam/isolate-path");
|
|
|
106
91
|
var import_isolate_timers2 = require("@ricsam/isolate-timers");
|
|
107
92
|
var import_isolate_test_environment2 = require("@ricsam/isolate-test-environment");
|
|
108
93
|
var import_isolate_playwright2 = require("@ricsam/isolate-playwright");
|
|
109
|
-
__reExport(exports_src, require("./internal.cjs"), module.exports);
|
|
110
94
|
var iteratorSessions = new Map;
|
|
111
95
|
var nextIteratorId = 1;
|
|
112
96
|
var ISOLATE_MARSHAL_CODE = `
|
|
@@ -232,6 +216,68 @@ var ISOLATE_MARSHAL_CODE = `
|
|
|
232
216
|
}
|
|
233
217
|
return fd;
|
|
234
218
|
}
|
|
219
|
+
case 'CallbackRef': {
|
|
220
|
+
// Create a proxy function that invokes the callback
|
|
221
|
+
const callbackId = value.callbackId;
|
|
222
|
+
return function(...args) {
|
|
223
|
+
const argsJson = JSON.stringify(marshalForHost(args));
|
|
224
|
+
const resultJson = __customFn_invoke.applySyncPromise(undefined, [callbackId, argsJson]);
|
|
225
|
+
const result = JSON.parse(resultJson);
|
|
226
|
+
if (result.ok) {
|
|
227
|
+
return unmarshalFromHost(result.value);
|
|
228
|
+
} else {
|
|
229
|
+
const error = new Error(result.error.message);
|
|
230
|
+
error.name = result.error.name;
|
|
231
|
+
throw error;
|
|
232
|
+
}
|
|
233
|
+
};
|
|
234
|
+
}
|
|
235
|
+
case 'PromiseRef': {
|
|
236
|
+
// Create a proxy Promise that resolves via callback
|
|
237
|
+
const promiseId = value.promiseId;
|
|
238
|
+
return new Promise((resolve, reject) => {
|
|
239
|
+
try {
|
|
240
|
+
const argsJson = JSON.stringify([promiseId]);
|
|
241
|
+
const resultJson = __customFn_invoke.applySyncPromise(undefined, [value.__resolveCallbackId, argsJson]);
|
|
242
|
+
const result = JSON.parse(resultJson);
|
|
243
|
+
if (result.ok) {
|
|
244
|
+
resolve(unmarshalFromHost(result.value));
|
|
245
|
+
} else {
|
|
246
|
+
reject(new Error(result.error.message));
|
|
247
|
+
}
|
|
248
|
+
} catch (e) {
|
|
249
|
+
reject(e);
|
|
250
|
+
}
|
|
251
|
+
});
|
|
252
|
+
}
|
|
253
|
+
case 'AsyncIteratorRef': {
|
|
254
|
+
const iteratorId = value.iteratorId;
|
|
255
|
+
const nextCallbackId = value.__nextCallbackId;
|
|
256
|
+
const returnCallbackId = value.__returnCallbackId;
|
|
257
|
+
return {
|
|
258
|
+
[Symbol.asyncIterator]() { return this; },
|
|
259
|
+
async next() {
|
|
260
|
+
const argsJson = JSON.stringify([iteratorId]);
|
|
261
|
+
const resultJson = __customFn_invoke.applySyncPromise(undefined, [nextCallbackId, argsJson]);
|
|
262
|
+
const result = JSON.parse(resultJson);
|
|
263
|
+
if (!result.ok) {
|
|
264
|
+
const error = new Error(result.error.message);
|
|
265
|
+
error.name = result.error.name;
|
|
266
|
+
throw error;
|
|
267
|
+
}
|
|
268
|
+
return {
|
|
269
|
+
done: result.value.done,
|
|
270
|
+
value: unmarshalFromHost(result.value.value)
|
|
271
|
+
};
|
|
272
|
+
},
|
|
273
|
+
async return(v) {
|
|
274
|
+
const argsJson = JSON.stringify([iteratorId, marshalForHost(v)]);
|
|
275
|
+
const resultJson = __customFn_invoke.applySyncPromise(undefined, [returnCallbackId, argsJson]);
|
|
276
|
+
const result = JSON.parse(resultJson);
|
|
277
|
+
return { done: true, value: result.ok ? unmarshalFromHost(result.value) : undefined };
|
|
278
|
+
}
|
|
279
|
+
};
|
|
280
|
+
}
|
|
235
281
|
default:
|
|
236
282
|
// Unknown ref type, return as-is
|
|
237
283
|
break;
|
|
@@ -255,9 +301,27 @@ var ISOLATE_MARSHAL_CODE = `
|
|
|
255
301
|
globalThis.__unmarshalFromHost = unmarshalFromHost;
|
|
256
302
|
})();
|
|
257
303
|
`;
|
|
258
|
-
async function setupCustomFunctions(context, customFunctions) {
|
|
304
|
+
async function setupCustomFunctions(context, customFunctions, marshalOptions) {
|
|
259
305
|
const global = context.global;
|
|
260
|
-
const invokeCallbackRef = new import_isolated_vm.default.Reference(async (
|
|
306
|
+
const invokeCallbackRef = new import_isolated_vm.default.Reference(async (nameOrId, argsJson) => {
|
|
307
|
+
if (typeof nameOrId === "number" && marshalOptions) {
|
|
308
|
+
const rawArgs2 = JSON.parse(argsJson);
|
|
309
|
+
const args2 = import_isolate_protocol3.unmarshalValue(rawArgs2);
|
|
310
|
+
try {
|
|
311
|
+
const result = await marshalOptions.invokeCallback(nameOrId, args2);
|
|
312
|
+
const ctx = marshalOptions.createMarshalContext();
|
|
313
|
+
const marshalledResult = await import_isolate_protocol3.marshalValue(result, ctx);
|
|
314
|
+
const processedResult = marshalOptions.addCallbackIdsToRefs(marshalledResult);
|
|
315
|
+
return JSON.stringify({ ok: true, value: processedResult });
|
|
316
|
+
} catch (error) {
|
|
317
|
+
const err = error;
|
|
318
|
+
return JSON.stringify({
|
|
319
|
+
ok: false,
|
|
320
|
+
error: { message: err.message, name: err.name }
|
|
321
|
+
});
|
|
322
|
+
}
|
|
323
|
+
}
|
|
324
|
+
const name = String(nameOrId);
|
|
261
325
|
const def = customFunctions[name];
|
|
262
326
|
if (!def) {
|
|
263
327
|
return JSON.stringify({
|
|
@@ -271,7 +335,13 @@ async function setupCustomFunctions(context, customFunctions) {
|
|
|
271
335
|
const rawArgs = JSON.parse(argsJson);
|
|
272
336
|
const args = import_isolate_protocol3.unmarshalValue(rawArgs);
|
|
273
337
|
try {
|
|
274
|
-
const result =
|
|
338
|
+
const result = await def.fn(...args);
|
|
339
|
+
if (marshalOptions) {
|
|
340
|
+
const ctx = marshalOptions.createMarshalContext();
|
|
341
|
+
const marshalledResult2 = await import_isolate_protocol3.marshalValue(result, ctx);
|
|
342
|
+
const processedResult = marshalOptions.addCallbackIdsToRefs(marshalledResult2);
|
|
343
|
+
return JSON.stringify({ ok: true, value: processedResult });
|
|
344
|
+
}
|
|
275
345
|
const marshalledResult = await import_isolate_protocol3.marshalValue(result);
|
|
276
346
|
return JSON.stringify({ ok: true, value: marshalledResult });
|
|
277
347
|
} catch (error) {
|
|
@@ -327,7 +397,14 @@ async function setupCustomFunctions(context, customFunctions) {
|
|
|
327
397
|
if (result.done) {
|
|
328
398
|
iteratorSessions.delete(iteratorId);
|
|
329
399
|
}
|
|
330
|
-
|
|
400
|
+
let marshalledValue;
|
|
401
|
+
if (marshalOptions) {
|
|
402
|
+
const ctx = marshalOptions.createMarshalContext();
|
|
403
|
+
marshalledValue = await import_isolate_protocol3.marshalValue(result.value, ctx);
|
|
404
|
+
marshalledValue = marshalOptions.addCallbackIdsToRefs(marshalledValue);
|
|
405
|
+
} else {
|
|
406
|
+
marshalledValue = await import_isolate_protocol3.marshalValue(result.value);
|
|
407
|
+
}
|
|
331
408
|
return JSON.stringify({
|
|
332
409
|
ok: true,
|
|
333
410
|
done: result.done,
|
|
@@ -353,7 +430,14 @@ async function setupCustomFunctions(context, customFunctions) {
|
|
|
353
430
|
const value = import_isolate_protocol3.unmarshalValue(rawValue);
|
|
354
431
|
const result = await session.iterator.return?.(value);
|
|
355
432
|
iteratorSessions.delete(iteratorId);
|
|
356
|
-
|
|
433
|
+
let marshalledValue;
|
|
434
|
+
if (marshalOptions) {
|
|
435
|
+
const ctx = marshalOptions.createMarshalContext();
|
|
436
|
+
marshalledValue = await import_isolate_protocol3.marshalValue(result?.value, ctx);
|
|
437
|
+
marshalledValue = marshalOptions.addCallbackIdsToRefs(marshalledValue);
|
|
438
|
+
} else {
|
|
439
|
+
marshalledValue = await import_isolate_protocol3.marshalValue(result?.value);
|
|
440
|
+
}
|
|
357
441
|
return JSON.stringify({ ok: true, done: true, value: marshalledValue });
|
|
358
442
|
} catch (error) {
|
|
359
443
|
const err = error;
|
|
@@ -383,7 +467,14 @@ async function setupCustomFunctions(context, customFunctions) {
|
|
|
383
467
|
});
|
|
384
468
|
const result = await session.iterator.throw?.(error);
|
|
385
469
|
iteratorSessions.delete(iteratorId);
|
|
386
|
-
|
|
470
|
+
let marshalledValue;
|
|
471
|
+
if (marshalOptions) {
|
|
472
|
+
const ctx = marshalOptions.createMarshalContext();
|
|
473
|
+
marshalledValue = await import_isolate_protocol3.marshalValue(result?.value, ctx);
|
|
474
|
+
marshalledValue = marshalOptions.addCallbackIdsToRefs(marshalledValue);
|
|
475
|
+
} else {
|
|
476
|
+
marshalledValue = await import_isolate_protocol3.marshalValue(result?.value);
|
|
477
|
+
}
|
|
387
478
|
return JSON.stringify({
|
|
388
479
|
ok: true,
|
|
389
480
|
done: result?.done ?? true,
|
|
@@ -474,8 +565,114 @@ async function setupCustomFunctions(context, customFunctions) {
|
|
|
474
565
|
}
|
|
475
566
|
return invokeCallbackRef;
|
|
476
567
|
}
|
|
568
|
+
function createLocalCustomFunctionsMarshalOptions() {
|
|
569
|
+
const returnedCallbacks = new Map;
|
|
570
|
+
const returnedPromises = new Map;
|
|
571
|
+
const returnedIterators = new Map;
|
|
572
|
+
let nextLocalCallbackId = 1e6;
|
|
573
|
+
const createMarshalContext = () => ({
|
|
574
|
+
registerCallback: (fn) => {
|
|
575
|
+
const callbackId = nextLocalCallbackId++;
|
|
576
|
+
returnedCallbacks.set(callbackId, fn);
|
|
577
|
+
return callbackId;
|
|
578
|
+
},
|
|
579
|
+
registerPromise: (promise) => {
|
|
580
|
+
const promiseId = nextLocalCallbackId++;
|
|
581
|
+
returnedPromises.set(promiseId, promise);
|
|
582
|
+
return promiseId;
|
|
583
|
+
},
|
|
584
|
+
registerIterator: (iterator) => {
|
|
585
|
+
const iteratorId = nextLocalCallbackId++;
|
|
586
|
+
returnedIterators.set(iteratorId, iterator);
|
|
587
|
+
return iteratorId;
|
|
588
|
+
}
|
|
589
|
+
});
|
|
590
|
+
const isPromiseRef = (value) => typeof value === "object" && value !== null && value.__type === "PromiseRef";
|
|
591
|
+
const isAsyncIteratorRef = (value) => typeof value === "object" && value !== null && value.__type === "AsyncIteratorRef";
|
|
592
|
+
const addCallbackIdsToRefs = (value) => {
|
|
593
|
+
if (value === null || typeof value !== "object")
|
|
594
|
+
return value;
|
|
595
|
+
if (isPromiseRef(value)) {
|
|
596
|
+
if ("__resolveCallbackId" in value)
|
|
597
|
+
return value;
|
|
598
|
+
const resolveCallbackId = nextLocalCallbackId++;
|
|
599
|
+
returnedCallbacks.set(resolveCallbackId, async (promiseId) => {
|
|
600
|
+
const promise = returnedPromises.get(promiseId);
|
|
601
|
+
if (!promise) {
|
|
602
|
+
throw new Error(`Promise ${promiseId} not found`);
|
|
603
|
+
}
|
|
604
|
+
const result2 = await promise;
|
|
605
|
+
returnedPromises.delete(promiseId);
|
|
606
|
+
const ctx = createMarshalContext();
|
|
607
|
+
const marshalled = await import_isolate_protocol3.marshalValue(result2, ctx);
|
|
608
|
+
return addCallbackIdsToRefs(marshalled);
|
|
609
|
+
});
|
|
610
|
+
return { ...value, __resolveCallbackId: resolveCallbackId };
|
|
611
|
+
}
|
|
612
|
+
if (isAsyncIteratorRef(value)) {
|
|
613
|
+
if ("__nextCallbackId" in value)
|
|
614
|
+
return value;
|
|
615
|
+
const nextCallbackId = nextLocalCallbackId++;
|
|
616
|
+
returnedCallbacks.set(nextCallbackId, async (iteratorId) => {
|
|
617
|
+
const iterator = returnedIterators.get(iteratorId);
|
|
618
|
+
if (!iterator) {
|
|
619
|
+
throw new Error(`Iterator ${iteratorId} not found`);
|
|
620
|
+
}
|
|
621
|
+
const result2 = await iterator.next();
|
|
622
|
+
if (result2.done) {
|
|
623
|
+
returnedIterators.delete(iteratorId);
|
|
624
|
+
}
|
|
625
|
+
const ctx = createMarshalContext();
|
|
626
|
+
const marshalledValue = await import_isolate_protocol3.marshalValue(result2.value, ctx);
|
|
627
|
+
return {
|
|
628
|
+
done: result2.done,
|
|
629
|
+
value: addCallbackIdsToRefs(marshalledValue)
|
|
630
|
+
};
|
|
631
|
+
});
|
|
632
|
+
const returnCallbackId = nextLocalCallbackId++;
|
|
633
|
+
returnedCallbacks.set(returnCallbackId, async (iteratorId, returnValue) => {
|
|
634
|
+
const iterator = returnedIterators.get(iteratorId);
|
|
635
|
+
returnedIterators.delete(iteratorId);
|
|
636
|
+
if (!iterator || !iterator.return) {
|
|
637
|
+
return { done: true, value: undefined };
|
|
638
|
+
}
|
|
639
|
+
const result2 = await iterator.return(returnValue);
|
|
640
|
+
const ctx = createMarshalContext();
|
|
641
|
+
const marshalledValue = await import_isolate_protocol3.marshalValue(result2.value, ctx);
|
|
642
|
+
return {
|
|
643
|
+
done: true,
|
|
644
|
+
value: addCallbackIdsToRefs(marshalledValue)
|
|
645
|
+
};
|
|
646
|
+
});
|
|
647
|
+
return {
|
|
648
|
+
...value,
|
|
649
|
+
__nextCallbackId: nextCallbackId,
|
|
650
|
+
__returnCallbackId: returnCallbackId
|
|
651
|
+
};
|
|
652
|
+
}
|
|
653
|
+
if (Array.isArray(value)) {
|
|
654
|
+
return value.map((item) => addCallbackIdsToRefs(item));
|
|
655
|
+
}
|
|
656
|
+
const result = {};
|
|
657
|
+
for (const key of Object.keys(value)) {
|
|
658
|
+
result[key] = addCallbackIdsToRefs(value[key]);
|
|
659
|
+
}
|
|
660
|
+
return result;
|
|
661
|
+
};
|
|
662
|
+
const invokeCallback = async (callbackId, args) => {
|
|
663
|
+
const callback = returnedCallbacks.get(callbackId);
|
|
664
|
+
if (!callback) {
|
|
665
|
+
throw new Error(`Local callback ${callbackId} not found`);
|
|
666
|
+
}
|
|
667
|
+
return await callback(...args);
|
|
668
|
+
};
|
|
669
|
+
return { createMarshalContext, addCallbackIdsToRefs, invokeCallback };
|
|
670
|
+
}
|
|
477
671
|
function createModuleResolver(state) {
|
|
478
672
|
return async (specifier, referrer) => {
|
|
673
|
+
const staticCached = state.staticModuleCache.get(specifier);
|
|
674
|
+
if (staticCached)
|
|
675
|
+
return staticCached;
|
|
479
676
|
const cached = state.moduleCache.get(specifier);
|
|
480
677
|
if (cached)
|
|
481
678
|
return cached;
|
|
@@ -484,29 +681,74 @@ function createModuleResolver(state) {
|
|
|
484
681
|
}
|
|
485
682
|
const importerPath = state.moduleToFilename.get(referrer) ?? "<unknown>";
|
|
486
683
|
const importerResolveDir = import_node_path.default.posix.dirname(importerPath);
|
|
487
|
-
const
|
|
684
|
+
const result = await state.moduleLoader(specifier, {
|
|
488
685
|
path: importerPath,
|
|
489
686
|
resolveDir: importerResolveDir
|
|
490
687
|
});
|
|
688
|
+
const { code, resolveDir } = result;
|
|
491
689
|
const hash = import_isolate_transform.contentHash(code);
|
|
492
690
|
const cacheKey = `${specifier}:${hash}`;
|
|
691
|
+
const inFlightKey = `${result.static ? "static" : "dynamic"}:${cacheKey}`;
|
|
692
|
+
const staticCachedAfterLoad = state.staticModuleCache.get(specifier);
|
|
693
|
+
if (staticCachedAfterLoad)
|
|
694
|
+
return staticCachedAfterLoad;
|
|
695
|
+
const cachedAfterLoad = state.moduleCache.get(specifier);
|
|
696
|
+
if (cachedAfterLoad)
|
|
697
|
+
return cachedAfterLoad;
|
|
493
698
|
const hashCached = state.moduleCache.get(cacheKey);
|
|
494
699
|
if (hashCached)
|
|
495
700
|
return hashCached;
|
|
496
|
-
const
|
|
497
|
-
if (
|
|
498
|
-
|
|
701
|
+
const inFlight = state.moduleLoadsInFlight.get(inFlightKey);
|
|
702
|
+
if (inFlight)
|
|
703
|
+
return inFlight;
|
|
704
|
+
const loadPromise = (async () => {
|
|
705
|
+
let mod;
|
|
706
|
+
try {
|
|
707
|
+
let transformed = state.transformCache.get(hash);
|
|
708
|
+
if (!transformed) {
|
|
709
|
+
transformed = await import_isolate_transform.transformModuleCode(code, specifier);
|
|
710
|
+
state.transformCache.set(hash, transformed);
|
|
711
|
+
}
|
|
712
|
+
if (transformed.sourceMap) {
|
|
713
|
+
state.sourceMaps.set(specifier, transformed.sourceMap);
|
|
714
|
+
}
|
|
715
|
+
mod = await state.isolate.compileModule(transformed.code, {
|
|
716
|
+
filename: specifier
|
|
717
|
+
});
|
|
718
|
+
const resolvedPath = import_node_path.default.posix.join(resolveDir, import_node_path.default.posix.basename(specifier));
|
|
719
|
+
state.moduleToFilename.set(mod, resolvedPath);
|
|
720
|
+
if (result.static) {
|
|
721
|
+
state.staticModuleCache.set(specifier, mod);
|
|
722
|
+
} else {
|
|
723
|
+
state.moduleCache.set(specifier, mod);
|
|
724
|
+
state.moduleCache.set(cacheKey, mod);
|
|
725
|
+
}
|
|
726
|
+
return mod;
|
|
727
|
+
} catch (err) {
|
|
728
|
+
if (mod) {
|
|
729
|
+
state.moduleToFilename.delete(mod);
|
|
730
|
+
if (result.static) {
|
|
731
|
+
if (state.staticModuleCache.get(specifier) === mod) {
|
|
732
|
+
state.staticModuleCache.delete(specifier);
|
|
733
|
+
}
|
|
734
|
+
} else {
|
|
735
|
+
if (state.moduleCache.get(specifier) === mod) {
|
|
736
|
+
state.moduleCache.delete(specifier);
|
|
737
|
+
}
|
|
738
|
+
if (state.moduleCache.get(cacheKey) === mod) {
|
|
739
|
+
state.moduleCache.delete(cacheKey);
|
|
740
|
+
}
|
|
741
|
+
}
|
|
742
|
+
}
|
|
743
|
+
throw err;
|
|
744
|
+
}
|
|
745
|
+
})();
|
|
746
|
+
state.moduleLoadsInFlight.set(inFlightKey, loadPromise);
|
|
747
|
+
try {
|
|
748
|
+
return await loadPromise;
|
|
749
|
+
} finally {
|
|
750
|
+
state.moduleLoadsInFlight.delete(inFlightKey);
|
|
499
751
|
}
|
|
500
|
-
const mod = await state.isolate.compileModule(transformed.code, {
|
|
501
|
-
filename: specifier
|
|
502
|
-
});
|
|
503
|
-
const resolvedPath = import_node_path.default.posix.join(resolveDir, import_node_path.default.posix.basename(specifier));
|
|
504
|
-
state.moduleToFilename.set(mod, resolvedPath);
|
|
505
|
-
state.moduleCache.set(specifier, mod);
|
|
506
|
-
state.moduleCache.set(cacheKey, mod);
|
|
507
|
-
const resolver = createModuleResolver(state);
|
|
508
|
-
await mod.instantiate(state.context, resolver);
|
|
509
|
-
return mod;
|
|
510
752
|
};
|
|
511
753
|
}
|
|
512
754
|
function convertFetchCallback(callback) {
|
|
@@ -514,8 +756,8 @@ function convertFetchCallback(callback) {
|
|
|
514
756
|
return {};
|
|
515
757
|
}
|
|
516
758
|
return {
|
|
517
|
-
onFetch: async (
|
|
518
|
-
return Promise.resolve(callback(
|
|
759
|
+
onFetch: async (url, init) => {
|
|
760
|
+
return Promise.resolve(callback(url, init));
|
|
519
761
|
}
|
|
520
762
|
};
|
|
521
763
|
}
|
|
@@ -531,8 +773,13 @@ async function createRuntime(options) {
|
|
|
531
773
|
context,
|
|
532
774
|
handles: {},
|
|
533
775
|
moduleCache: new Map,
|
|
776
|
+
staticModuleCache: new Map,
|
|
777
|
+
moduleLoadsInFlight: new Map,
|
|
778
|
+
transformCache: new Map,
|
|
534
779
|
moduleToFilename: new Map,
|
|
535
780
|
sourceMaps: new Map,
|
|
781
|
+
pendingCallbacks: [],
|
|
782
|
+
evalChain: Promise.resolve(),
|
|
536
783
|
moduleLoader: opts.moduleLoader,
|
|
537
784
|
customFunctions: opts.customFunctions
|
|
538
785
|
};
|
|
@@ -547,13 +794,17 @@ async function createRuntime(options) {
|
|
|
547
794
|
state.handles.fs = await import_isolate_fs.setupFs(context, opts.fs);
|
|
548
795
|
}
|
|
549
796
|
if (opts.customFunctions) {
|
|
550
|
-
|
|
797
|
+
const customMarshalOptions = opts.customFunctionsMarshalOptions ?? createLocalCustomFunctionsMarshalOptions();
|
|
798
|
+
state.customFnInvokeRef = await setupCustomFunctions(context, opts.customFunctions, customMarshalOptions);
|
|
551
799
|
}
|
|
552
800
|
if (opts.testEnvironment) {
|
|
553
801
|
const testEnvOptions = typeof opts.testEnvironment === "object" ? opts.testEnvironment : undefined;
|
|
554
802
|
state.handles.testEnvironment = await import_isolate_test_environment.setupTestEnvironment(context, testEnvOptions);
|
|
555
803
|
}
|
|
556
804
|
if (opts.playwright) {
|
|
805
|
+
if (!opts.playwright.handler) {
|
|
806
|
+
throw new Error("Playwright configured without handler. Provide playwright.handler in createRuntime options.");
|
|
807
|
+
}
|
|
557
808
|
let eventCallback = opts.playwright.onEvent;
|
|
558
809
|
if (opts.playwright.console && opts.console?.onEntry) {
|
|
559
810
|
const originalCallback = eventCallback;
|
|
@@ -572,12 +823,13 @@ async function createRuntime(options) {
|
|
|
572
823
|
}
|
|
573
824
|
};
|
|
574
825
|
}
|
|
575
|
-
|
|
576
|
-
|
|
826
|
+
const playwrightSetupOptions = {
|
|
827
|
+
handler: opts.playwright.handler,
|
|
577
828
|
timeout: opts.playwright.timeout,
|
|
578
829
|
console: opts.playwright.console && !opts.console?.onEntry,
|
|
579
830
|
onEvent: eventCallback
|
|
580
|
-
}
|
|
831
|
+
};
|
|
832
|
+
state.handles.playwright = await import_isolate_playwright.setupPlaywright(context, playwrightSetupOptions);
|
|
581
833
|
}
|
|
582
834
|
const fetchHandle = {
|
|
583
835
|
async dispatchRequest(request, options2) {
|
|
@@ -633,6 +885,48 @@ async function createRuntime(options) {
|
|
|
633
885
|
throw new Error("Fetch handle not available");
|
|
634
886
|
}
|
|
635
887
|
return state.handles.fetch.hasActiveConnections();
|
|
888
|
+
},
|
|
889
|
+
dispatchClientWebSocketOpen(socketId, protocol, extensions) {
|
|
890
|
+
if (!state.handles.fetch) {
|
|
891
|
+
throw new Error("Fetch handle not available");
|
|
892
|
+
}
|
|
893
|
+
state.handles.fetch.dispatchClientWebSocketOpen(socketId, protocol, extensions);
|
|
894
|
+
},
|
|
895
|
+
dispatchClientWebSocketMessage(socketId, data) {
|
|
896
|
+
if (!state.handles.fetch) {
|
|
897
|
+
throw new Error("Fetch handle not available");
|
|
898
|
+
}
|
|
899
|
+
state.handles.fetch.dispatchClientWebSocketMessage(socketId, data);
|
|
900
|
+
},
|
|
901
|
+
dispatchClientWebSocketClose(socketId, code, reason, wasClean) {
|
|
902
|
+
if (!state.handles.fetch) {
|
|
903
|
+
throw new Error("Fetch handle not available");
|
|
904
|
+
}
|
|
905
|
+
state.handles.fetch.dispatchClientWebSocketClose(socketId, code, reason, wasClean);
|
|
906
|
+
},
|
|
907
|
+
dispatchClientWebSocketError(socketId) {
|
|
908
|
+
if (!state.handles.fetch) {
|
|
909
|
+
throw new Error("Fetch handle not available");
|
|
910
|
+
}
|
|
911
|
+
state.handles.fetch.dispatchClientWebSocketError(socketId);
|
|
912
|
+
},
|
|
913
|
+
onClientWebSocketCommand(callback) {
|
|
914
|
+
if (!state.handles.fetch) {
|
|
915
|
+
throw new Error("Fetch handle not available");
|
|
916
|
+
}
|
|
917
|
+
return state.handles.fetch.onClientWebSocketCommand(callback);
|
|
918
|
+
},
|
|
919
|
+
onEvent(callback) {
|
|
920
|
+
if (!state.handles.fetch) {
|
|
921
|
+
throw new Error("Fetch handle not available");
|
|
922
|
+
}
|
|
923
|
+
return state.handles.fetch.onEvent(callback);
|
|
924
|
+
},
|
|
925
|
+
dispatchEvent(event, payload) {
|
|
926
|
+
if (!state.handles.fetch) {
|
|
927
|
+
throw new Error("Fetch handle not available");
|
|
928
|
+
}
|
|
929
|
+
state.handles.fetch.dispatchEvent(event, payload);
|
|
636
930
|
}
|
|
637
931
|
};
|
|
638
932
|
const timersHandle = {
|
|
@@ -655,11 +949,27 @@ async function createRuntime(options) {
|
|
|
655
949
|
}
|
|
656
950
|
};
|
|
657
951
|
const testEnvironmentHandle = {
|
|
658
|
-
async runTests(
|
|
952
|
+
async runTests(timeout) {
|
|
659
953
|
if (!state.handles.testEnvironment) {
|
|
660
954
|
throw new Error("Test environment not enabled. Set testEnvironment: true in createRuntime options.");
|
|
661
955
|
}
|
|
662
|
-
|
|
956
|
+
if (timeout === undefined) {
|
|
957
|
+
return import_isolate_test_environment.runTests(state.context);
|
|
958
|
+
}
|
|
959
|
+
let timeoutId;
|
|
960
|
+
const timeoutPromise = new Promise((_, reject) => {
|
|
961
|
+
timeoutId = setTimeout(() => reject(new Error("Test timeout")), timeout);
|
|
962
|
+
});
|
|
963
|
+
try {
|
|
964
|
+
return await Promise.race([
|
|
965
|
+
import_isolate_test_environment.runTests(state.context),
|
|
966
|
+
timeoutPromise
|
|
967
|
+
]);
|
|
968
|
+
} finally {
|
|
969
|
+
if (timeoutId) {
|
|
970
|
+
clearTimeout(timeoutId);
|
|
971
|
+
}
|
|
972
|
+
}
|
|
663
973
|
},
|
|
664
974
|
hasTests() {
|
|
665
975
|
if (!state.handles.testEnvironment) {
|
|
@@ -680,7 +990,7 @@ async function createRuntime(options) {
|
|
|
680
990
|
const playwrightHandle = {
|
|
681
991
|
getCollectedData() {
|
|
682
992
|
if (!state.handles.playwright) {
|
|
683
|
-
throw new Error("Playwright not configured. Provide playwright.
|
|
993
|
+
throw new Error("Playwright not configured. Provide playwright.handler in createRuntime options.");
|
|
684
994
|
}
|
|
685
995
|
return {
|
|
686
996
|
browserConsoleLogs: state.handles.playwright.getBrowserConsoleLogs(),
|
|
@@ -694,43 +1004,62 @@ async function createRuntime(options) {
|
|
|
694
1004
|
};
|
|
695
1005
|
return {
|
|
696
1006
|
id,
|
|
1007
|
+
pendingCallbacks: state.pendingCallbacks,
|
|
697
1008
|
fetch: fetchHandle,
|
|
698
1009
|
timers: timersHandle,
|
|
699
1010
|
console: consoleHandle,
|
|
700
1011
|
testEnvironment: testEnvironmentHandle,
|
|
701
1012
|
playwright: playwrightHandle,
|
|
702
1013
|
async eval(code, filenameOrOptions) {
|
|
703
|
-
const
|
|
704
|
-
|
|
705
|
-
|
|
706
|
-
const transformed = await import_isolate_transform.transformEntryCode(code, filename);
|
|
707
|
-
if (transformed.sourceMap) {
|
|
708
|
-
state.sourceMaps.set(filename, transformed.sourceMap);
|
|
709
|
-
}
|
|
710
|
-
const mod = await state.isolate.compileModule(transformed.code, {
|
|
711
|
-
filename
|
|
712
|
-
});
|
|
713
|
-
state.moduleToFilename.set(mod, filename);
|
|
714
|
-
const resolver = createModuleResolver(state);
|
|
715
|
-
await mod.instantiate(state.context, resolver);
|
|
716
|
-
await mod.evaluate();
|
|
717
|
-
const ns = mod.namespace;
|
|
718
|
-
const runRef = await ns.get("default", { reference: true });
|
|
1014
|
+
const runEval = async () => {
|
|
1015
|
+
const options2 = typeof filenameOrOptions === "string" ? { filename: filenameOrOptions } : filenameOrOptions;
|
|
1016
|
+
const filename = import_isolate_protocol.normalizeEntryFilename(options2?.filename);
|
|
719
1017
|
try {
|
|
720
|
-
await
|
|
721
|
-
|
|
722
|
-
|
|
1018
|
+
const transformed = await import_isolate_transform.transformEntryCode(code, filename);
|
|
1019
|
+
if (transformed.sourceMap) {
|
|
1020
|
+
state.sourceMaps.set(filename, transformed.sourceMap);
|
|
1021
|
+
}
|
|
1022
|
+
const mod = await state.isolate.compileModule(transformed.code, {
|
|
1023
|
+
filename
|
|
723
1024
|
});
|
|
724
|
-
|
|
725
|
-
|
|
726
|
-
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
1025
|
+
state.moduleToFilename.set(mod, filename);
|
|
1026
|
+
const resolver = createModuleResolver(state);
|
|
1027
|
+
await mod.instantiate(state.context, resolver);
|
|
1028
|
+
await mod.evaluate();
|
|
1029
|
+
const ns = mod.namespace;
|
|
1030
|
+
const runRef = await ns.get("default", { reference: true });
|
|
1031
|
+
try {
|
|
1032
|
+
await runRef.apply(undefined, [], {
|
|
1033
|
+
result: { promise: true }
|
|
1034
|
+
});
|
|
1035
|
+
} finally {
|
|
1036
|
+
runRef.release();
|
|
1037
|
+
}
|
|
1038
|
+
if (state.pendingCallbacks.length > 0) {
|
|
1039
|
+
await Promise.all(state.pendingCallbacks);
|
|
1040
|
+
state.pendingCallbacks.length = 0;
|
|
1041
|
+
}
|
|
1042
|
+
} catch (err) {
|
|
1043
|
+
const error = err;
|
|
1044
|
+
if (error.stack && state.sourceMaps.size > 0) {
|
|
1045
|
+
error.stack = import_isolate_transform.mapErrorStack(error.stack, state.sourceMaps);
|
|
1046
|
+
}
|
|
1047
|
+
throw error;
|
|
731
1048
|
}
|
|
732
|
-
|
|
733
|
-
|
|
1049
|
+
};
|
|
1050
|
+
const queuedEval = state.evalChain.then(runEval, runEval);
|
|
1051
|
+
state.evalChain = queuedEval.then(() => {
|
|
1052
|
+
return;
|
|
1053
|
+
}, () => {
|
|
1054
|
+
return;
|
|
1055
|
+
});
|
|
1056
|
+
return queuedEval;
|
|
1057
|
+
},
|
|
1058
|
+
clearModuleCache() {
|
|
1059
|
+
state.moduleCache.clear();
|
|
1060
|
+
state.moduleLoadsInFlight.clear();
|
|
1061
|
+
state.moduleToFilename.clear();
|
|
1062
|
+
state.sourceMaps.clear();
|
|
734
1063
|
},
|
|
735
1064
|
async dispose() {
|
|
736
1065
|
if (state.customFnInvokeRef) {
|
|
@@ -747,10 +1076,11 @@ async function createRuntime(options) {
|
|
|
747
1076
|
state.handles.console?.dispose();
|
|
748
1077
|
state.handles.core?.dispose();
|
|
749
1078
|
state.moduleCache.clear();
|
|
1079
|
+
state.moduleLoadsInFlight.clear();
|
|
750
1080
|
state.context.release();
|
|
751
1081
|
state.isolate.dispose();
|
|
752
1082
|
}
|
|
753
1083
|
};
|
|
754
1084
|
}
|
|
755
1085
|
|
|
756
|
-
//# debugId=
|
|
1086
|
+
//# debugId=9159E7F9BC462BBB64756E2164756E21
|