@ricsam/isolate 0.1.3 → 0.1.5

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 (80) hide show
  1. package/README.md +25 -2
  2. package/dist/cjs/internal/async-context/index.cjs +140 -0
  3. package/dist/cjs/internal/async-context/index.cjs.map +10 -0
  4. package/dist/cjs/internal/client/connection.cjs +175 -123
  5. package/dist/cjs/internal/client/connection.cjs.map +3 -3
  6. package/dist/cjs/internal/console/index.cjs +2 -2
  7. package/dist/cjs/internal/console/index.cjs.map +2 -2
  8. package/dist/cjs/internal/core/index.cjs +13 -5
  9. package/dist/cjs/internal/core/index.cjs.map +3 -3
  10. package/dist/cjs/internal/crypto/index.cjs +2 -2
  11. package/dist/cjs/internal/crypto/index.cjs.map +2 -2
  12. package/dist/cjs/internal/daemon/connection.cjs +77 -12
  13. package/dist/cjs/internal/daemon/connection.cjs.map +3 -3
  14. package/dist/cjs/internal/encoding/index.cjs.map +1 -1
  15. package/dist/cjs/internal/fetch/index.cjs +80 -18
  16. package/dist/cjs/internal/fetch/index.cjs.map +3 -3
  17. package/dist/cjs/internal/fetch/stream-state.cjs.map +1 -1
  18. package/dist/cjs/internal/fs/index.cjs +2 -2
  19. package/dist/cjs/internal/fs/index.cjs.map +2 -2
  20. package/dist/cjs/internal/module-loader/bundle.cjs +225 -8
  21. package/dist/cjs/internal/module-loader/bundle.cjs.map +3 -3
  22. package/dist/cjs/internal/path/index.cjs.map +1 -1
  23. package/dist/cjs/internal/playwright/index.cjs +2 -2
  24. package/dist/cjs/internal/playwright/index.cjs.map +2 -2
  25. package/dist/cjs/internal/runtime/index.cjs +78 -6
  26. package/dist/cjs/internal/runtime/index.cjs.map +3 -3
  27. package/dist/cjs/internal/test-environment/index.cjs +2 -2
  28. package/dist/cjs/internal/test-environment/index.cjs.map +2 -2
  29. package/dist/cjs/internal/timers/index.cjs +9 -4
  30. package/dist/cjs/internal/timers/index.cjs.map +3 -3
  31. package/dist/cjs/internal/typecheck/isolate-types.cjs +36 -1
  32. package/dist/cjs/internal/typecheck/isolate-types.cjs.map +3 -3
  33. package/dist/cjs/package.json +1 -1
  34. package/dist/mjs/internal/async-context/index.mjs +100 -0
  35. package/dist/mjs/internal/async-context/index.mjs.map +10 -0
  36. package/dist/mjs/internal/client/connection.mjs +176 -123
  37. package/dist/mjs/internal/client/connection.mjs.map +3 -3
  38. package/dist/mjs/internal/console/index.mjs +2 -2
  39. package/dist/mjs/internal/console/index.mjs.map +2 -2
  40. package/dist/mjs/internal/core/index.mjs +13 -5
  41. package/dist/mjs/internal/core/index.mjs.map +3 -3
  42. package/dist/mjs/internal/crypto/index.mjs +2 -2
  43. package/dist/mjs/internal/crypto/index.mjs.map +2 -2
  44. package/dist/mjs/internal/daemon/connection.mjs +77 -12
  45. package/dist/mjs/internal/daemon/connection.mjs.map +3 -3
  46. package/dist/mjs/internal/encoding/index.mjs.map +1 -1
  47. package/dist/mjs/internal/fetch/index.mjs +80 -18
  48. package/dist/mjs/internal/fetch/index.mjs.map +3 -3
  49. package/dist/mjs/internal/fetch/stream-state.mjs.map +1 -1
  50. package/dist/mjs/internal/fs/index.mjs +2 -2
  51. package/dist/mjs/internal/fs/index.mjs.map +2 -2
  52. package/dist/mjs/internal/module-loader/bundle.mjs +225 -8
  53. package/dist/mjs/internal/module-loader/bundle.mjs.map +3 -3
  54. package/dist/mjs/internal/path/index.mjs.map +1 -1
  55. package/dist/mjs/internal/playwright/index.mjs +2 -2
  56. package/dist/mjs/internal/playwright/index.mjs.map +2 -2
  57. package/dist/mjs/internal/runtime/index.mjs +78 -6
  58. package/dist/mjs/internal/runtime/index.mjs.map +3 -3
  59. package/dist/mjs/internal/test-environment/index.mjs +2 -2
  60. package/dist/mjs/internal/test-environment/index.mjs.map +2 -2
  61. package/dist/mjs/internal/timers/index.mjs +9 -4
  62. package/dist/mjs/internal/timers/index.mjs.map +3 -3
  63. package/dist/mjs/internal/typecheck/isolate-types.mjs +36 -1
  64. package/dist/mjs/internal/typecheck/isolate-types.mjs.map +3 -3
  65. package/dist/mjs/package.json +1 -1
  66. package/dist/types/internal/async-context/index.d.ts +5 -0
  67. package/dist/types/internal/console/index.d.ts +1 -1
  68. package/dist/types/internal/core/index.d.ts +2 -2
  69. package/dist/types/internal/crypto/index.d.ts +1 -1
  70. package/dist/types/internal/daemon/types.d.ts +1 -0
  71. package/dist/types/internal/encoding/index.d.ts +1 -1
  72. package/dist/types/internal/fetch/index.d.ts +1 -1
  73. package/dist/types/internal/fetch/stream-state.d.ts +1 -1
  74. package/dist/types/internal/fs/index.d.ts +1 -1
  75. package/dist/types/internal/path/index.d.ts +1 -1
  76. package/dist/types/internal/playwright/index.d.ts +1 -1
  77. package/dist/types/internal/test-environment/index.d.ts +1 -1
  78. package/dist/types/internal/timers/index.d.ts +1 -1
  79. package/dist/types/internal/typecheck/isolate-types.d.ts +2 -2
  80. package/package.json +8 -3
package/README.md CHANGED
@@ -1,13 +1,15 @@
1
1
  # @ricsam/isolate
2
2
 
3
- `@ricsam/isolate` is a runtime-centric JavaScript sandbox built on [`isolated-vm`](https://github.com/nicknisi/isolated-vm). It gives you a single host API for running isolated code with web-style capabilities such as `fetch`, files, streams, server handlers, module loading, and Playwright-backed browser tests.
3
+ `@ricsam/isolate` is a runtime-centric JavaScript sandbox built on an async-context-enabled [`@ricsam/isolated-vm`](https://github.com/ricsam/isolated-vm) engine build. It gives you a single host API for running isolated code with web-style capabilities such as `fetch`, files, streams, server handlers, module loading, and Playwright-backed browser tests.
4
4
 
5
5
  ## Installation
6
6
 
7
7
  ```bash
8
- npm add @ricsam/isolate isolated-vm
8
+ npm add @ricsam/isolate @ricsam/isolated-vm
9
9
  ```
10
10
 
11
+ The `@ricsam/isolated-vm` peer includes the `createContext({ asyncContext: true })` support required by this repo. Upstream `isolated-vm` will fail fast during runtime boot with a clear AsyncContext error.
12
+
11
13
  Install Playwright when you want browser runtimes:
12
14
 
13
15
  ```bash
@@ -41,6 +43,27 @@ Each runtime is configured through `bindings`, which describe how sandboxed code
41
43
 
42
44
  Every host callback receives a `HostCallContext` with an `AbortSignal`, runtime identity, resource identity, and request metadata.
43
45
 
46
+ ## Async Context
47
+
48
+ Runtimes created by `@ricsam/isolate` enable the TC39 proposal-style `AsyncContext` global inside the sandbox. This is an experimental surface for now, and the proposal API is used to implement the `node:async_hooks` shim exported to sandboxed code.
49
+
50
+ This shim is intended for async context propagation inside the sandbox. It is not a full reimplementation of Node's `async_hooks` lifecycle, resource graph, or profiling APIs.
51
+
52
+ What is currently supported:
53
+
54
+ - `AsyncContext.Variable`
55
+ - `AsyncContext.Snapshot`
56
+ - `node:async_hooks` `AsyncLocalStorage`
57
+ - `node:async_hooks` `AsyncResource`
58
+
59
+ What is intentionally not implemented in `node:async_hooks` yet:
60
+
61
+ - `createHook()`
62
+ - `executionAsyncId()`
63
+ - `triggerAsyncId()`
64
+ - `executionAsyncResource()`
65
+ - `asyncWrapProviders`
66
+
44
67
  ## Quick Start
45
68
 
46
69
  ```ts
@@ -0,0 +1,140 @@
1
+ var __defProp = Object.defineProperty;
2
+ var __getOwnPropNames = Object.getOwnPropertyNames;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
5
+ function __accessProp(key) {
6
+ return this[key];
7
+ }
8
+ var __toCommonJS = (from) => {
9
+ var entry = (__moduleCache ??= new WeakMap).get(from), desc;
10
+ if (entry)
11
+ return entry;
12
+ entry = __defProp({}, "__esModule", { value: true });
13
+ if (from && typeof from === "object" || typeof from === "function") {
14
+ for (var key of __getOwnPropNames(from))
15
+ if (!__hasOwnProp.call(entry, key))
16
+ __defProp(entry, key, {
17
+ get: __accessProp.bind(from, key),
18
+ enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable
19
+ });
20
+ }
21
+ __moduleCache.set(from, entry);
22
+ return entry;
23
+ };
24
+ var __moduleCache;
25
+ var __returnValue = (v) => v;
26
+ function __exportSetter(name, newValue) {
27
+ this[name] = __returnValue.bind(null, newValue);
28
+ }
29
+ var __export = (target, all) => {
30
+ for (var name in all)
31
+ __defProp(target, name, {
32
+ get: all[name],
33
+ enumerable: true,
34
+ configurable: true,
35
+ set: __exportSetter.bind(all, name)
36
+ });
37
+ };
38
+
39
+ // src/internal/async-context/index.ts
40
+ var exports_async_context = {};
41
+ __export(exports_async_context, {
42
+ setupAsyncContext: () => setupAsyncContext
43
+ });
44
+ module.exports = __toCommonJS(exports_async_context);
45
+ var ASYNC_CONTEXT_BOOTSTRAP = `
46
+ (function() {
47
+ if (globalThis.__isolateAsyncContextInternals) {
48
+ return;
49
+ }
50
+
51
+ const AsyncContext = globalThis.AsyncContext;
52
+ const native = globalThis.__ivmAsyncContextInternal;
53
+ if (
54
+ !AsyncContext
55
+ || typeof AsyncContext.Variable !== "function"
56
+ || typeof AsyncContext.Snapshot !== "function"
57
+ || !native
58
+ || typeof native.getContinuationPreservedEmbedderData !== "function"
59
+ || typeof native.setContinuationPreservedEmbedderData !== "function"
60
+ ) {
61
+ throw new Error(
62
+ "The installed isolated-vm runtime does not expose async context support. " +
63
+ "Install the async-context-enabled isolate engine build."
64
+ );
65
+ }
66
+
67
+ class AsyncContextFrame extends Map {
68
+ constructor(store, value) {
69
+ super(AsyncContextFrame.current() ?? undefined);
70
+ if (arguments.length > 0) {
71
+ this.set(store, value);
72
+ }
73
+ }
74
+
75
+ static current() {
76
+ return native.getContinuationPreservedEmbedderData();
77
+ }
78
+
79
+ static set(frame) {
80
+ native.setContinuationPreservedEmbedderData(frame);
81
+ }
82
+
83
+ static exchange(frame) {
84
+ const prior = this.current();
85
+ this.set(frame);
86
+ return prior;
87
+ }
88
+
89
+ static disable(store) {
90
+ const frame = this.current();
91
+ frame?.delete(store);
92
+ }
93
+ }
94
+
95
+ Object.defineProperty(AsyncContextFrame, "enabled", {
96
+ configurable: true,
97
+ enumerable: false,
98
+ value: true,
99
+ });
100
+ const currentAsyncResource = new AsyncContext.Variable({
101
+ name: "isolate.asyncResource",
102
+ defaultValue: undefined,
103
+ });
104
+
105
+ const wrapCallback = (callback) => {
106
+ if (typeof callback !== "function") {
107
+ return callback;
108
+ }
109
+ return AsyncContext.Snapshot.wrap(callback);
110
+ };
111
+
112
+ Object.defineProperty(globalThis, "__isolateAsyncContextInternals", {
113
+ configurable: true,
114
+ enumerable: false,
115
+ writable: false,
116
+ value: {
117
+ AsyncContextFrame,
118
+ currentAsyncResource,
119
+ wrapCallback,
120
+ },
121
+ });
122
+ })();
123
+ `;
124
+ async function setupAsyncContext(context) {
125
+ const supported = context.evalSync(`
126
+ typeof globalThis.AsyncContext === "object"
127
+ && typeof globalThis.AsyncContext?.Variable === "function"
128
+ && typeof globalThis.AsyncContext?.Snapshot === "function"
129
+ && typeof globalThis.__ivmAsyncContextInternal === "object"
130
+ && typeof globalThis.__ivmAsyncContextInternal?.getContinuationPreservedEmbedderData === "function"
131
+ && typeof globalThis.__ivmAsyncContextInternal?.setContinuationPreservedEmbedderData === "function"
132
+ `);
133
+ if (!supported) {
134
+ throw new Error("The installed isolated-vm runtime does not support AsyncContext. " + "Use the async-context-enabled isolate engine build.");
135
+ }
136
+ context.evalSync(ASYNC_CONTEXT_BOOTSTRAP);
137
+ return { supported };
138
+ }
139
+
140
+ //# debugId=68BD605C0C0582DB64756E2164756E21
@@ -0,0 +1,10 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../../src/internal/async-context/index.ts"],
4
+ "sourcesContent": [
5
+ "import type ivm from \"@ricsam/isolated-vm\";\n\nconst ASYNC_CONTEXT_BOOTSTRAP = `\n(function() {\n if (globalThis.__isolateAsyncContextInternals) {\n return;\n }\n\n const AsyncContext = globalThis.AsyncContext;\n const native = globalThis.__ivmAsyncContextInternal;\n if (\n !AsyncContext\n || typeof AsyncContext.Variable !== \"function\"\n || typeof AsyncContext.Snapshot !== \"function\"\n || !native\n || typeof native.getContinuationPreservedEmbedderData !== \"function\"\n || typeof native.setContinuationPreservedEmbedderData !== \"function\"\n ) {\n throw new Error(\n \"The installed isolated-vm runtime does not expose async context support. \" +\n \"Install the async-context-enabled isolate engine build.\"\n );\n }\n\n class AsyncContextFrame extends Map {\n constructor(store, value) {\n super(AsyncContextFrame.current() ?? undefined);\n if (arguments.length > 0) {\n this.set(store, value);\n }\n }\n\n static current() {\n return native.getContinuationPreservedEmbedderData();\n }\n\n static set(frame) {\n native.setContinuationPreservedEmbedderData(frame);\n }\n\n static exchange(frame) {\n const prior = this.current();\n this.set(frame);\n return prior;\n }\n\n static disable(store) {\n const frame = this.current();\n frame?.delete(store);\n }\n }\n\n Object.defineProperty(AsyncContextFrame, \"enabled\", {\n configurable: true,\n enumerable: false,\n value: true,\n });\n const currentAsyncResource = new AsyncContext.Variable({\n name: \"isolate.asyncResource\",\n defaultValue: undefined,\n });\n\n const wrapCallback = (callback) => {\n if (typeof callback !== \"function\") {\n return callback;\n }\n return AsyncContext.Snapshot.wrap(callback);\n };\n\n Object.defineProperty(globalThis, \"__isolateAsyncContextInternals\", {\n configurable: true,\n enumerable: false,\n writable: false,\n value: {\n AsyncContextFrame,\n currentAsyncResource,\n wrapCallback,\n },\n });\n})();\n`;\n\nexport interface AsyncContextHandle {\n supported: boolean;\n}\n\nexport async function setupAsyncContext(context: ivm.Context): Promise<AsyncContextHandle> {\n const supported = context.evalSync(`\n typeof globalThis.AsyncContext === \"object\"\n && typeof globalThis.AsyncContext?.Variable === \"function\"\n && typeof globalThis.AsyncContext?.Snapshot === \"function\"\n && typeof globalThis.__ivmAsyncContextInternal === \"object\"\n && typeof globalThis.__ivmAsyncContextInternal?.getContinuationPreservedEmbedderData === \"function\"\n && typeof globalThis.__ivmAsyncContextInternal?.setContinuationPreservedEmbedderData === \"function\"\n `) as boolean;\n\n if (!supported) {\n throw new Error(\n \"The installed isolated-vm runtime does not support AsyncContext. \" +\n \"Use the async-context-enabled isolate engine build.\"\n );\n }\n\n context.evalSync(ASYNC_CONTEXT_BOOTSTRAP);\n return { supported };\n}\n"
6
+ ],
7
+ "mappings": ";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAEA,IAAM,0BAA0B;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAoFhC,eAAsB,iBAAiB,CAAC,SAAmD;AAAA,EACzF,MAAM,YAAY,QAAQ,SAAS;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,GAOlC;AAAA,EAED,IAAI,CAAC,WAAW;AAAA,IACd,MAAM,IAAI,MACR,sEACA,qDACF;AAAA,EACF;AAAA,EAEA,QAAQ,SAAS,uBAAuB;AAAA,EACxC,OAAO,EAAE,UAAU;AAAA;",
8
+ "debugId": "68BD605C0C0582DB64756E2164756E21",
9
+ "names": []
10
+ }
@@ -81,6 +81,7 @@ async function connect(options = {}) {
81
81
  const state = {
82
82
  socket,
83
83
  pendingRequests: new Map,
84
+ pendingCallbackCalls: new Map,
84
85
  callbacks: new Map,
85
86
  callbacksNeedingRequestId: new Set,
86
87
  nextRequestId: 1,
@@ -113,6 +114,10 @@ async function connect(options = {}) {
113
114
  pending.reject(new Error("Connection closed"));
114
115
  }
115
116
  state.pendingRequests.clear();
117
+ for (const [, pending] of state.pendingCallbackCalls) {
118
+ pending.reject(new Error("Connection closed"));
119
+ }
120
+ state.pendingCallbackCalls.clear();
116
121
  for (const [, receiver] of state.streamResponses) {
117
122
  receiver.state = "errored";
118
123
  receiver.error = new Error("Connection closed");
@@ -310,6 +315,24 @@ function handleMessage(message, state) {
310
315
  handleCallbackInvoke(invoke, state);
311
316
  break;
312
317
  }
318
+ case import_protocol.MessageType.CALLBACK_RESPONSE: {
319
+ const response = message;
320
+ const pending = state.pendingCallbackCalls.get(response.requestId);
321
+ if (pending) {
322
+ state.pendingCallbackCalls.delete(response.requestId);
323
+ if (response.error) {
324
+ const error = new Error(response.error.message);
325
+ error.name = response.error.name;
326
+ if (response.error.stack) {
327
+ error.stack = response.error.stack;
328
+ }
329
+ pending.reject(error);
330
+ } else {
331
+ pending.resolve(response.result);
332
+ }
333
+ }
334
+ break;
335
+ }
313
336
  case import_protocol.MessageType.PONG:
314
337
  break;
315
338
  case import_protocol.MessageType.CALLBACK_STREAM_CANCEL: {
@@ -550,6 +573,27 @@ async function handleCallbackInvoke(invoke, state) {
550
573
  }
551
574
  }
552
575
  }
576
+ function invokeDaemonCallback(state, callbackId, args) {
577
+ if (!state.connected) {
578
+ return Promise.reject(new Error("Not connected"));
579
+ }
580
+ const requestId = state.nextRequestId++;
581
+ const requestContext = import_request_context.getRequestContext();
582
+ const invoke = {
583
+ type: import_protocol.MessageType.CALLBACK_INVOKE,
584
+ requestId,
585
+ callbackId,
586
+ args,
587
+ context: requestContext ? {
588
+ requestId: requestContext.requestId,
589
+ metadata: requestContext.metadata
590
+ } : undefined
591
+ };
592
+ return new Promise((resolve, reject) => {
593
+ state.pendingCallbackCalls.set(requestId, { resolve, reject });
594
+ sendMessage(state.socket, invoke);
595
+ });
596
+ }
553
597
  function sendMessage(socket, message) {
554
598
  const frame = import_protocol.buildFrame(message);
555
599
  socket.write(frame);
@@ -1416,13 +1460,141 @@ var returnedPromiseRegistry = new Map;
1416
1460
  var returnedIteratorRegistry = new Map;
1417
1461
  function registerCustomFunctions(state, customFunctions) {
1418
1462
  const registrations = {};
1463
+ const addCallbackIdsToRefs = (value) => {
1464
+ if (value === null || typeof value !== "object") {
1465
+ return value;
1466
+ }
1467
+ if (import_protocol.isPromiseRef(value)) {
1468
+ const resolveCallbackId = state.nextCallbackId++;
1469
+ state.callbacks.set(resolveCallbackId, async (...args) => {
1470
+ const promiseId = args[0];
1471
+ const promise = returnedPromiseRegistry.get(promiseId);
1472
+ if (!promise) {
1473
+ throw new Error(`Promise ${promiseId} not found`);
1474
+ }
1475
+ const promiseResult = await promise;
1476
+ returnedPromiseRegistry.delete(promiseId);
1477
+ const marshalledResult = await import_protocol.marshalValue(promiseResult, marshalCtx);
1478
+ return addCallbackIdsToRefs(marshalledResult);
1479
+ });
1480
+ return {
1481
+ ...value,
1482
+ __resolveCallbackId: resolveCallbackId
1483
+ };
1484
+ }
1485
+ if (import_protocol.isAsyncIteratorRef(value)) {
1486
+ const nextCallbackId = state.nextCallbackId++;
1487
+ state.callbacks.set(nextCallbackId, async (...args) => {
1488
+ const iteratorId = args[0];
1489
+ const iterator = returnedIteratorRegistry.get(iteratorId);
1490
+ if (!iterator) {
1491
+ throw new Error(`Iterator ${iteratorId} not found`);
1492
+ }
1493
+ const iterResult = await iterator.next();
1494
+ if (iterResult.done) {
1495
+ returnedIteratorRegistry.delete(iteratorId);
1496
+ }
1497
+ const marshalledValue = await import_protocol.marshalValue(iterResult.value, marshalCtx);
1498
+ return {
1499
+ done: iterResult.done,
1500
+ value: addCallbackIdsToRefs(marshalledValue)
1501
+ };
1502
+ });
1503
+ const returnCallbackId = state.nextCallbackId++;
1504
+ state.callbacks.set(returnCallbackId, async (...args) => {
1505
+ const iteratorId = args[0];
1506
+ const returnValue = args[1];
1507
+ const iterator = returnedIteratorRegistry.get(iteratorId);
1508
+ returnedIteratorRegistry.delete(iteratorId);
1509
+ if (!iterator || !iterator.return) {
1510
+ return { done: true, value: undefined };
1511
+ }
1512
+ const iterResult = await iterator.return(returnValue);
1513
+ const marshalledValue = await import_protocol.marshalValue(iterResult.value, marshalCtx);
1514
+ return {
1515
+ done: true,
1516
+ value: addCallbackIdsToRefs(marshalledValue)
1517
+ };
1518
+ });
1519
+ const throwCallbackId = state.nextCallbackId++;
1520
+ state.callbacks.set(throwCallbackId, async (...args) => {
1521
+ const iteratorId = args[0];
1522
+ const errorValue = args[1];
1523
+ const iterator = returnedIteratorRegistry.get(iteratorId);
1524
+ if (!iterator) {
1525
+ throw new Error(`Iterator ${iteratorId} not found`);
1526
+ }
1527
+ try {
1528
+ if (!iterator.throw) {
1529
+ throw Object.assign(new Error(errorValue?.message ?? "Iterator does not support throw()"), { name: errorValue?.name ?? "Error", stack: errorValue?.stack });
1530
+ }
1531
+ const thrownError = Object.assign(new Error(errorValue?.message ?? "Iterator throw()"), { name: errorValue?.name ?? "Error", stack: errorValue?.stack });
1532
+ const iterResult = await iterator.throw(thrownError);
1533
+ if (iterResult.done) {
1534
+ returnedIteratorRegistry.delete(iteratorId);
1535
+ }
1536
+ const marshalledValue = await import_protocol.marshalValue(iterResult.value, marshalCtx);
1537
+ return {
1538
+ done: iterResult.done,
1539
+ value: addCallbackIdsToRefs(marshalledValue)
1540
+ };
1541
+ } catch (error) {
1542
+ returnedIteratorRegistry.delete(iteratorId);
1543
+ throw error;
1544
+ }
1545
+ });
1546
+ return {
1547
+ ...value,
1548
+ __nextCallbackId: nextCallbackId,
1549
+ __returnCallbackId: returnCallbackId,
1550
+ __throwCallbackId: throwCallbackId
1551
+ };
1552
+ }
1553
+ if (Array.isArray(value)) {
1554
+ return value.map((item) => addCallbackIdsToRefs(item));
1555
+ }
1556
+ const objResult = {};
1557
+ for (const key of Object.keys(value)) {
1558
+ objResult[key] = addCallbackIdsToRefs(value[key]);
1559
+ }
1560
+ return objResult;
1561
+ };
1562
+ const marshalCtx = {
1563
+ registerCallback: (fn) => {
1564
+ const returnedCallbackId = state.nextCallbackId++;
1565
+ state.callbacks.set(returnedCallbackId, async (...args) => {
1566
+ const fnResult = await fn(...args);
1567
+ const marshalledResult = await import_protocol.marshalValue(fnResult, marshalCtx);
1568
+ return addCallbackIdsToRefs(marshalledResult);
1569
+ });
1570
+ return returnedCallbackId;
1571
+ },
1572
+ registerPromise: (promise) => {
1573
+ const promiseId = state.nextCallbackId++;
1574
+ returnedPromiseRegistry.set(promiseId, promise);
1575
+ return promiseId;
1576
+ },
1577
+ registerIterator: (iterator) => {
1578
+ const iteratorId = state.nextCallbackId++;
1579
+ returnedIteratorRegistry.set(iteratorId, iterator);
1580
+ return iteratorId;
1581
+ }
1582
+ };
1583
+ const unmarshalCtx = {};
1584
+ unmarshalCtx.getCallback = (callbackId) => {
1585
+ return async (...args) => {
1586
+ const marshalledArgs = await import_protocol.marshalValue(args, marshalCtx);
1587
+ const result = await invokeDaemonCallback(state, callbackId, addCallbackIdsToRefs(marshalledArgs));
1588
+ return import_protocol.unmarshalValue(result, unmarshalCtx);
1589
+ };
1590
+ };
1419
1591
  for (const [name, def] of Object.entries(customFunctions)) {
1420
1592
  if (def.type === "asyncIterator") {
1421
1593
  const startCallbackId = state.nextCallbackId++;
1422
1594
  state.callbacks.set(startCallbackId, async (...args) => {
1423
1595
  try {
1424
1596
  const fn = def.fn;
1425
- const iterator = fn(...args);
1597
+ const iterator = fn(...import_protocol.unmarshalValue(args, unmarshalCtx));
1426
1598
  const iteratorId = nextClientIteratorId++;
1427
1599
  clientIteratorSessions.set(iteratorId, { iterator });
1428
1600
  return { iteratorId };
@@ -1491,127 +1663,7 @@ function registerCustomFunctions(state, customFunctions) {
1491
1663
  } else {
1492
1664
  const callbackId = state.nextCallbackId++;
1493
1665
  state.callbacks.set(callbackId, async (...args) => {
1494
- const result = await def.fn(...args);
1495
- const addCallbackIdsToRefs = (value) => {
1496
- if (value === null || typeof value !== "object") {
1497
- return value;
1498
- }
1499
- if (import_protocol.isPromiseRef(value)) {
1500
- const resolveCallbackId = state.nextCallbackId++;
1501
- state.callbacks.set(resolveCallbackId, async (...args2) => {
1502
- const promiseId = args2[0];
1503
- const promise = returnedPromiseRegistry.get(promiseId);
1504
- if (!promise) {
1505
- throw new Error(`Promise ${promiseId} not found`);
1506
- }
1507
- const promiseResult = await promise;
1508
- returnedPromiseRegistry.delete(promiseId);
1509
- const marshalledResult = await import_protocol.marshalValue(promiseResult, marshalCtx);
1510
- return addCallbackIdsToRefs(marshalledResult);
1511
- });
1512
- return {
1513
- ...value,
1514
- __resolveCallbackId: resolveCallbackId
1515
- };
1516
- }
1517
- if (import_protocol.isAsyncIteratorRef(value)) {
1518
- const nextCallbackId = state.nextCallbackId++;
1519
- state.callbacks.set(nextCallbackId, async (...args2) => {
1520
- const iteratorId = args2[0];
1521
- const iterator = returnedIteratorRegistry.get(iteratorId);
1522
- if (!iterator) {
1523
- throw new Error(`Iterator ${iteratorId} not found`);
1524
- }
1525
- const iterResult = await iterator.next();
1526
- if (iterResult.done) {
1527
- returnedIteratorRegistry.delete(iteratorId);
1528
- }
1529
- const marshalledValue = await import_protocol.marshalValue(iterResult.value, marshalCtx);
1530
- return {
1531
- done: iterResult.done,
1532
- value: addCallbackIdsToRefs(marshalledValue)
1533
- };
1534
- });
1535
- const returnCallbackId = state.nextCallbackId++;
1536
- state.callbacks.set(returnCallbackId, async (...args2) => {
1537
- const iteratorId = args2[0];
1538
- const returnValue = args2[1];
1539
- const iterator = returnedIteratorRegistry.get(iteratorId);
1540
- returnedIteratorRegistry.delete(iteratorId);
1541
- if (!iterator || !iterator.return) {
1542
- return { done: true, value: undefined };
1543
- }
1544
- const iterResult = await iterator.return(returnValue);
1545
- const marshalledValue = await import_protocol.marshalValue(iterResult.value, marshalCtx);
1546
- return {
1547
- done: true,
1548
- value: addCallbackIdsToRefs(marshalledValue)
1549
- };
1550
- });
1551
- const throwCallbackId = state.nextCallbackId++;
1552
- state.callbacks.set(throwCallbackId, async (...args2) => {
1553
- const iteratorId = args2[0];
1554
- const errorValue = args2[1];
1555
- const iterator = returnedIteratorRegistry.get(iteratorId);
1556
- if (!iterator) {
1557
- throw new Error(`Iterator ${iteratorId} not found`);
1558
- }
1559
- try {
1560
- if (!iterator.throw) {
1561
- throw Object.assign(new Error(errorValue?.message ?? "Iterator does not support throw()"), { name: errorValue?.name ?? "Error", stack: errorValue?.stack });
1562
- }
1563
- const thrownError = Object.assign(new Error(errorValue?.message ?? "Iterator throw()"), { name: errorValue?.name ?? "Error", stack: errorValue?.stack });
1564
- const iterResult = await iterator.throw(thrownError);
1565
- if (iterResult.done) {
1566
- returnedIteratorRegistry.delete(iteratorId);
1567
- }
1568
- const marshalledValue = await import_protocol.marshalValue(iterResult.value, marshalCtx);
1569
- return {
1570
- done: iterResult.done,
1571
- value: addCallbackIdsToRefs(marshalledValue)
1572
- };
1573
- } catch (error) {
1574
- returnedIteratorRegistry.delete(iteratorId);
1575
- throw error;
1576
- }
1577
- });
1578
- return {
1579
- ...value,
1580
- __nextCallbackId: nextCallbackId,
1581
- __returnCallbackId: returnCallbackId,
1582
- __throwCallbackId: throwCallbackId
1583
- };
1584
- }
1585
- if (Array.isArray(value)) {
1586
- return value.map((item) => addCallbackIdsToRefs(item));
1587
- }
1588
- const objResult = {};
1589
- for (const key of Object.keys(value)) {
1590
- objResult[key] = addCallbackIdsToRefs(value[key]);
1591
- }
1592
- return objResult;
1593
- };
1594
- const marshalCtx = {
1595
- registerCallback: (fn) => {
1596
- const returnedCallbackId = state.nextCallbackId++;
1597
- state.callbacks.set(returnedCallbackId, async (...args2) => {
1598
- const fnResult = await fn(...args2);
1599
- const marshalledResult = await import_protocol.marshalValue(fnResult, marshalCtx);
1600
- return addCallbackIdsToRefs(marshalledResult);
1601
- });
1602
- return returnedCallbackId;
1603
- },
1604
- registerPromise: (promise) => {
1605
- const promiseId = state.nextCallbackId++;
1606
- returnedPromiseRegistry.set(promiseId, promise);
1607
- return promiseId;
1608
- },
1609
- registerIterator: (iterator) => {
1610
- const iteratorId = state.nextCallbackId++;
1611
- returnedIteratorRegistry.set(iteratorId, iterator);
1612
- return iteratorId;
1613
- }
1614
- };
1666
+ const result = await def.fn(...import_protocol.unmarshalValue(args, unmarshalCtx));
1615
1667
  const marshalled = await import_protocol.marshalValue(result, marshalCtx);
1616
1668
  const withCallbackIds = addCallbackIdsToRefs(marshalled);
1617
1669
  return withCallbackIds;
@@ -1916,4 +1968,4 @@ function handleClientWsClose(isolateId, payload, state) {
1916
1968
  }
1917
1969
  }
1918
1970
 
1919
- //# debugId=7D1BE4A52F267ED264756E2164756E21
1971
+ //# debugId=6EEF0F611807A4E264756E2164756E21