@jsii/kernel 1.61.0 → 1.63.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.
@@ -0,0 +1,3 @@
1
+ import config from '../../../jest.config.mjs';
2
+
3
+ export default config;
package/lib/kernel.d.ts CHANGED
@@ -5,15 +5,16 @@ export declare class Kernel {
5
5
  * Set to true for verbose debugging.
6
6
  */
7
7
  traceEnabled: boolean;
8
- private assemblies;
8
+ private readonly assemblies;
9
9
  private readonly objects;
10
- private cbs;
11
- private waiting;
12
- private promises;
10
+ private readonly cbs;
11
+ private readonly waiting;
12
+ private readonly promises;
13
13
  private nextid;
14
14
  private syncInProgress?;
15
15
  private installDir?;
16
- private readonly sandbox;
16
+ /** The internal require function, used instead of the global "require" so that webpack does not transform it... */
17
+ private require?;
17
18
  /**
18
19
  * Creates a jsii kernel object.
19
20
  *
@@ -74,17 +75,5 @@ export declare class Kernel {
74
75
  private _findPropertyTarget;
75
76
  private _makecbid;
76
77
  private _makeprid;
77
- private _wrapSandboxCode;
78
- /**
79
- * Executes arbitrary code in a VM sandbox.
80
- *
81
- * @param code JavaScript code to be executed in the VM
82
- * @param sandbox a VM context to use for running the code
83
- * @param sourceMaps source maps to be used in case an exception is thrown
84
- * @param filename the file name to use for the executed code
85
- *
86
- * @returns the result of evaluating the code
87
- */
88
- private _execute;
89
78
  }
90
79
  //# sourceMappingURL=kernel.d.ts.map
package/lib/kernel.js CHANGED
@@ -2,12 +2,13 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.Kernel = void 0;
4
4
  const spec = require("@jsii/spec");
5
+ const spec_1 = require("@jsii/spec");
5
6
  const cp = require("child_process");
6
7
  const fs = require("fs-extra");
8
+ const module_1 = require("module");
7
9
  const os = require("os");
8
10
  const path = require("path");
9
11
  const tar = require("tar");
10
- const vm = require("vm");
11
12
  const api = require("./api");
12
13
  const api_1 = require("./api");
13
14
  const objects_1 = require("./objects");
@@ -22,35 +23,20 @@ class Kernel {
22
23
  * result (or throw an error).
23
24
  */
24
25
  constructor(callbackHandler) {
25
- // `setImmediate` is required for tests to pass (it is otherwise
26
- // impossible to wait for in-VM promises to complete)
27
26
  this.callbackHandler = callbackHandler;
28
27
  /**
29
28
  * Set to true for verbose debugging.
30
29
  */
31
30
  this.traceEnabled = false;
32
- this.assemblies = {};
31
+ this.assemblies = new Map();
33
32
  this.objects = new objects_1.ObjectTable(this._typeInfoForFqn.bind(this));
34
- this.cbs = {};
35
- this.waiting = {};
36
- this.promises = {};
33
+ this.cbs = new Map();
34
+ this.waiting = new Map();
35
+ this.promises = new Map();
37
36
  this.nextid = 20000; // incrementing counter for objid, cbid, promiseid
38
- // `Buffer` is required when using simple-resource-bundler.
39
- // HACK: when we webpack @jsii/runtime, all "require" statements get transpiled,
40
- // so modules can be resolved within the pack. However, here we actually want to
41
- // let loaded modules to use the native node "require" method.
42
- // I wonder if webpack has some pragma that allows opting-out at certain points
43
- // in the code.
44
- // eslint-disable-next-line @typescript-eslint/no-require-imports,@typescript-eslint/no-var-requires
45
- const moduleLoad = require('module').Module._load;
46
- const nodeRequire = (p) => moduleLoad(p, module, false);
47
- this.sandbox = vm.createContext({
48
- Buffer,
49
- setImmediate,
50
- require: nodeRequire, // modules need to "require"
51
- });
52
37
  }
53
38
  load(req) {
39
+ var _a, _b;
54
40
  this._debug('load', req);
55
41
  if ('assembly' in req) {
56
42
  throw new Error('`assembly` field is deprecated for "load", use `name`, `version` and `tarball` instead');
@@ -69,10 +55,10 @@ class Kernel {
69
55
  }
70
56
  // same version, no-op
71
57
  this._debug('look up already-loaded assembly', pkgname);
72
- const assm = this.assemblies[pkgname];
58
+ const assm = this.assemblies.get(pkgname);
73
59
  return {
74
60
  assembly: assm.metadata.name,
75
- types: Object.keys(assm.metadata.types ?? {}).length,
61
+ types: Object.keys((_a = assm.metadata.types) !== null && _a !== void 0 ? _a : {}).length,
76
62
  };
77
63
  }
78
64
  // Create the install directory (there may be several path components for @scoped/packages)
@@ -95,21 +81,24 @@ class Kernel {
95
81
  process.umask(originalUmask);
96
82
  }
97
83
  // read .jsii metadata from the root of the package
98
- const jsiiMetadataFile = path.join(packageDir, spec.SPEC_FILE_NAME);
99
- if (!fs.pathExistsSync(jsiiMetadataFile)) {
100
- throw new Error(`Package tarball ${req.tarball} must have a file named ${spec.SPEC_FILE_NAME} at the root`);
84
+ let assmSpec;
85
+ try {
86
+ assmSpec = (0, spec_1.loadAssemblyFromPath)(packageDir);
87
+ }
88
+ catch (e) {
89
+ throw new Error(`Error for package tarball ${req.tarball}: ${e.message}`);
101
90
  }
102
- const assmSpec = fs.readJsonSync(jsiiMetadataFile);
103
- // load the module and capture it's closure
104
- const closure = this._execute(`require(String.raw\`${packageDir}\`)`, packageDir);
91
+ // load the module and capture its closure
92
+ const closure = this.require(packageDir);
105
93
  const assm = new Assembly(assmSpec, closure);
106
94
  this._addAssembly(assm);
107
95
  return {
108
96
  assembly: assmSpec.name,
109
- types: Object.keys(assmSpec.types ?? {}).length,
97
+ types: Object.keys((_b = assmSpec.types) !== null && _b !== void 0 ? _b : {}).length,
110
98
  };
111
99
  }
112
100
  invokeBinScript(req) {
101
+ var _a;
113
102
  const packageDir = this._getPackageDir(req.assembly);
114
103
  if (fs.pathExistsSync(packageDir)) {
115
104
  // module exists, verify version
@@ -121,7 +110,7 @@ class Kernel {
121
110
  if (!epkg.bin) {
122
111
  throw new Error(`Script with name ${req.script} was not defined.`);
123
112
  }
124
- const result = cp.spawnSync(path.join(packageDir, scriptPath), req.args ?? [], {
113
+ const result = cp.spawnSync(path.join(packageDir, scriptPath), (_a = req.args) !== null && _a !== void 0 ? _a : [], {
125
114
  encoding: 'utf-8',
126
115
  env: {
127
116
  ...process.env,
@@ -159,9 +148,9 @@ class Kernel {
159
148
  throw new Error(`property ${symbol} is not static`);
160
149
  }
161
150
  const prototype = this._findSymbol(fqn);
162
- const value = this._ensureSync(`property ${property}`, () => this._wrapSandboxCode(() => prototype[property]));
151
+ const value = this._ensureSync(`property ${property}`, () => prototype[property]);
163
152
  this._debug('value:', value);
164
- const ret = this._fromSandbox(value, ti);
153
+ const ret = this._fromSandbox(value, ti, `of static property ${symbol}`);
165
154
  this._debug('ret', ret);
166
155
  return { value: ret };
167
156
  }
@@ -177,7 +166,7 @@ class Kernel {
177
166
  throw new Error(`static property ${symbol} is readonly`);
178
167
  }
179
168
  const prototype = this._findSymbol(fqn);
180
- this._ensureSync(`property ${property}`, () => this._wrapSandboxCode(() => (prototype[property] = this._toSandbox(value, ti))));
169
+ this._ensureSync(`property ${property}`, () => (prototype[property] = this._toSandbox(value, ti, `assigned to static property ${symbol}`)));
181
170
  return {};
182
171
  }
183
172
  get(req) {
@@ -193,9 +182,9 @@ class Kernel {
193
182
  const propertyToGet = this._findPropertyTarget(instance, property);
194
183
  // make the actual "get", and block any async calls that might be performed
195
184
  // by jsii overrides.
196
- const value = this._ensureSync(`property '${objref[api_1.TOKEN_REF]}.${propertyToGet}'`, () => this._wrapSandboxCode(() => instance[propertyToGet]));
185
+ const value = this._ensureSync(`property '${objref[api_1.TOKEN_REF]}.${propertyToGet}'`, () => instance[propertyToGet]);
197
186
  this._debug('value:', value);
198
- const ret = this._fromSandbox(value, ti);
187
+ const ret = this._fromSandbox(value, ti, `of property ${fqn}.${property}`);
199
188
  this._debug('ret:', ret);
200
189
  return { value: ret };
201
190
  }
@@ -208,28 +197,31 @@ class Kernel {
208
197
  throw new Error(`Cannot set value of immutable property ${req.property} to ${req.value}`);
209
198
  }
210
199
  const propertyToSet = this._findPropertyTarget(instance, property);
211
- this._ensureSync(`property '${objref[api_1.TOKEN_REF]}.${propertyToSet}'`, () => this._wrapSandboxCode(() => (instance[propertyToSet] = this._toSandbox(value, propInfo))));
200
+ this._ensureSync(`property '${objref[api_1.TOKEN_REF]}.${propertyToSet}'`, () => (instance[propertyToSet] = this._toSandbox(value, propInfo, `assigned to property ${fqn}.${property}`)));
212
201
  return {};
213
202
  }
214
203
  invoke(req) {
204
+ var _a, _b;
215
205
  const { objref, method } = req;
216
- const args = req.args ?? [];
206
+ const args = (_a = req.args) !== null && _a !== void 0 ? _a : [];
217
207
  this._debug('invoke', objref, method, args);
218
208
  const { ti, obj, fn } = this._findInvokeTarget(objref, method, args);
219
209
  // verify this is not an async method
220
210
  if (ti.async) {
221
211
  throw new Error(`${method} is an async method, use "begin" instead`);
222
212
  }
213
+ const fqn = (0, objects_1.jsiiTypeFqn)(obj);
223
214
  const ret = this._ensureSync(`method '${objref[api_1.TOKEN_REF]}.${method}'`, () => {
224
- return this._wrapSandboxCode(() => fn.apply(obj, this._toSandboxValues(args, ti.parameters)));
215
+ return fn.apply(obj, this._toSandboxValues(args, `method ${fqn ? `${fqn}#` : ''}${method}`, ti.parameters));
225
216
  });
226
- const result = this._fromSandbox(ret, ti.returns ?? 'void');
217
+ const result = this._fromSandbox(ret, (_b = ti.returns) !== null && _b !== void 0 ? _b : 'void', `returned by method ${fqn ? `${fqn}#` : ''}${method}`);
227
218
  this._debug('invoke result', result);
228
219
  return { result };
229
220
  }
230
221
  sinvoke(req) {
222
+ var _a, _b;
231
223
  const { fqn, method } = req;
232
- const args = req.args ?? [];
224
+ const args = (_a = req.args) !== null && _a !== void 0 ? _a : [];
233
225
  this._debug('sinvoke', fqn, method, args);
234
226
  const ti = this._typeInfoForMethod(method, fqn);
235
227
  if (!ti.static) {
@@ -242,14 +234,17 @@ class Kernel {
242
234
  const prototype = this._findSymbol(fqn);
243
235
  const fn = prototype[method];
244
236
  const ret = this._ensureSync(`method '${fqn}.${method}'`, () => {
245
- return this._wrapSandboxCode(() => fn.apply(prototype, this._toSandboxValues(args, ti.parameters)));
237
+ return fn.apply(prototype, this._toSandboxValues(args, `static method ${fqn}.${method}`, ti.parameters));
246
238
  });
247
239
  this._debug('method returned:', ret);
248
- return { result: this._fromSandbox(ret, ti.returns ?? 'void') };
240
+ return {
241
+ result: this._fromSandbox(ret, (_b = ti.returns) !== null && _b !== void 0 ? _b : 'void', `returned by static method ${fqn}.${method}`),
242
+ };
249
243
  }
250
244
  begin(req) {
245
+ var _a;
251
246
  const { objref, method } = req;
252
- const args = req.args ?? [];
247
+ const args = (_a = req.args) !== null && _a !== void 0 ? _a : [];
253
248
  this._debug('begin', objref, method, args);
254
249
  if (this.syncInProgress) {
255
250
  throw new Error(`Cannot invoke async method '${req.objref[api_1.TOKEN_REF]}.${req.method}' while sync ${this.syncInProgress} is being processed`);
@@ -259,25 +254,28 @@ class Kernel {
259
254
  if (!ti.async) {
260
255
  throw new Error(`Method ${method} is expected to be an async method`);
261
256
  }
262
- const promise = this._wrapSandboxCode(() => fn.apply(obj, this._toSandboxValues(args, ti.parameters)));
257
+ const fqn = (0, objects_1.jsiiTypeFqn)(obj);
258
+ const promise = fn.apply(obj, this._toSandboxValues(args, `async method ${fqn ? `${fqn}#` : ''}${method}`, ti.parameters));
263
259
  // since we are planning to resolve this promise in a different scope
264
260
  // we need to handle rejections here [1]
265
261
  // [1]: https://stackoverflow.com/questions/40920179/should-i-refrain-from-handling-promise-rejection-asynchronously/40921505
266
262
  promise.catch((_) => undefined);
267
263
  const prid = this._makeprid();
268
- this.promises[prid] = {
264
+ this.promises.set(prid, {
269
265
  promise,
270
266
  method: ti,
271
- };
267
+ });
272
268
  return { promiseid: prid };
273
269
  }
274
270
  async end(req) {
271
+ var _a;
275
272
  const { promiseid } = req;
276
273
  this._debug('end', promiseid);
277
- const { promise, method } = this.promises[promiseid];
278
- if (promise == null) {
274
+ const storedPromise = this.promises.get(promiseid);
275
+ if (storedPromise == null) {
279
276
  throw new Error(`Cannot find promise with ID: ${promiseid}`);
280
277
  }
278
+ const { promise, method } = storedPromise;
281
279
  let result;
282
280
  try {
283
281
  result = await promise;
@@ -287,13 +285,15 @@ class Kernel {
287
285
  this._debug('promise error:', e);
288
286
  throw e;
289
287
  }
290
- return { result: this._fromSandbox(result, method.returns ?? 'void') };
288
+ return {
289
+ result: this._fromSandbox(result, (_a = method.returns) !== null && _a !== void 0 ? _a : 'void', `returned by async method ${method.name}`),
290
+ };
291
291
  }
292
292
  callbacks(_req) {
293
293
  this._debug('callbacks');
294
- const ret = Object.keys(this.cbs).map((cbid) => {
295
- const cb = this.cbs[cbid];
296
- this.waiting[cbid] = cb; // move to waiting
294
+ const ret = Array.from(this.cbs.entries()).map(([cbid, cb]) => {
295
+ this.waiting.set(cbid, cb); // move to waiting
296
+ this.cbs.delete(cbid); // remove from created
297
297
  const callback = {
298
298
  cbid,
299
299
  cookie: cb.override.cookie,
@@ -305,27 +305,26 @@ class Kernel {
305
305
  };
306
306
  return callback;
307
307
  });
308
- // move all callbacks to the wait queue and clean the callback queue.
309
- this.cbs = {};
310
308
  return { callbacks: ret };
311
309
  }
312
310
  complete(req) {
311
+ var _a;
313
312
  const { cbid, err, result } = req;
314
313
  this._debug('complete', cbid, err, result);
315
- if (!(cbid in this.waiting)) {
314
+ const cb = this.waiting.get(cbid);
315
+ if (!cb) {
316
316
  throw new Error(`Callback ${cbid} not found`);
317
317
  }
318
- const cb = this.waiting[cbid];
319
318
  if (err) {
320
319
  this._debug('completed with error:', err);
321
320
  cb.fail(new Error(err));
322
321
  }
323
322
  else {
324
- const sandoxResult = this._toSandbox(result, cb.expectedReturnType ?? 'void');
323
+ const sandoxResult = this._toSandbox(result, (_a = cb.expectedReturnType) !== null && _a !== void 0 ? _a : 'void', `returned by callback ${cb.toString()}`);
325
324
  this._debug('completed with result:', sandoxResult);
326
325
  cb.succeed(sandoxResult);
327
326
  }
328
- delete this.waiting[cbid];
327
+ this.waiting.delete(cbid);
329
328
  return { cbid };
330
329
  }
331
330
  /**
@@ -348,10 +347,11 @@ class Kernel {
348
347
  };
349
348
  }
350
349
  _addAssembly(assm) {
351
- this.assemblies[assm.metadata.name] = assm;
350
+ var _a;
351
+ this.assemblies.set(assm.metadata.name, assm);
352
352
  // add the __jsii__.fqn property on every constructor. this allows
353
353
  // traversing between the javascript and jsii worlds given any object.
354
- for (const fqn of Object.keys(assm.metadata.types ?? {})) {
354
+ for (const fqn of Object.keys((_a = assm.metadata.types) !== null && _a !== void 0 ? _a : {})) {
355
355
  const typedef = assm.metadata.types[fqn];
356
356
  switch (typedef.kind) {
357
357
  case spec.TypeKind.Interface:
@@ -386,6 +386,7 @@ class Kernel {
386
386
  _getPackageDir(pkgname) {
387
387
  if (!this.installDir) {
388
388
  this.installDir = fs.mkdtempSync(path.join(os.tmpdir(), 'jsii-kernel-'));
389
+ this.require = (0, module_1.createRequire)(this.installDir);
389
390
  fs.mkdirpSync(path.join(this.installDir, 'node_modules'));
390
391
  this._debug('creating jsii-kernel modules workdir:', this.installDir);
391
392
  onExit.removeSync(this.installDir);
@@ -395,13 +396,14 @@ class Kernel {
395
396
  // prefixed with _ to allow calling this method internally without
396
397
  // getting it recorded for testing.
397
398
  _create(req) {
399
+ var _a, _b;
398
400
  this._debug('create', req);
399
401
  const { fqn, interfaces, overrides } = req;
400
- const requestArgs = req.args ?? [];
402
+ const requestArgs = (_a = req.args) !== null && _a !== void 0 ? _a : [];
401
403
  const ctorResult = this._findCtor(fqn, requestArgs);
402
404
  const ctor = ctorResult.ctor;
403
- const obj = this._wrapSandboxCode(() => new ctor(...this._toSandboxValues(requestArgs, ctorResult.parameters)));
404
- const objref = this.objects.registerObject(obj, fqn, req.interfaces ?? []);
405
+ const obj = new ctor(...this._toSandboxValues(requestArgs, `new ${fqn}`, ctorResult.parameters));
406
+ const objref = this.objects.registerObject(obj, fqn, (_b = req.interfaces) !== null && _b !== void 0 ? _b : []);
405
407
  // overrides: for each one of the override method names, installs a
406
408
  // method on the newly created object which represents the remote "reverse proxy".
407
409
  if (overrides) {
@@ -466,11 +468,12 @@ class Kernel {
466
468
  this._defineOverridenProperty(obj, objref, override, propInfo);
467
469
  }
468
470
  _defineOverridenProperty(obj, objref, override, propInfo) {
471
+ var _a;
469
472
  const propertyName = override.property;
470
473
  this._debug('apply override', propertyName);
471
474
  // save the old property under $jsii$super$<prop>$ so that property overrides
472
475
  // can still access it via `super.<prop>`.
473
- const prev = getPropertyDescriptor(obj, propertyName) ?? {
476
+ const prev = (_a = getPropertyDescriptor(obj, propertyName)) !== null && _a !== void 0 ? _a : {
474
477
  value: obj[propertyName],
475
478
  writable: true,
476
479
  enumerable: true,
@@ -495,7 +498,7 @@ class Kernel {
495
498
  get: { objref, property: propertyName },
496
499
  });
497
500
  this._debug('callback returned', result);
498
- return this._toSandbox(result, propInfo);
501
+ return this._toSandbox(result, propInfo, `returned by callback property ${propertyName}`);
499
502
  },
500
503
  set: (value) => {
501
504
  this._debug('virtual set', objref, propertyName, {
@@ -507,7 +510,7 @@ class Kernel {
507
510
  set: {
508
511
  objref,
509
512
  property: propertyName,
510
- value: this._fromSandbox(value, propInfo),
513
+ value: this._fromSandbox(value, propInfo, `assigned to callback property ${propertyName}`),
511
514
  },
512
515
  });
513
516
  },
@@ -558,6 +561,8 @@ class Kernel {
558
561
  }
559
562
  _defineOverridenMethod(obj, objref, override, methodInfo) {
560
563
  const methodName = override.method;
564
+ const fqn = (0, objects_1.jsiiTypeFqn)(obj);
565
+ const methodContext = `${methodInfo.async ? 'async ' : ''}method${fqn ? `${fqn}#` : methodName}`;
561
566
  if (methodInfo.async) {
562
567
  // async method override
563
568
  Object.defineProperty(obj, methodName, {
@@ -566,18 +571,19 @@ class Kernel {
566
571
  writable: false,
567
572
  value: (...methodArgs) => {
568
573
  this._debug('invoke async method override', override);
569
- const args = this._toSandboxValues(methodArgs, methodInfo.parameters);
574
+ const args = this._toSandboxValues(methodArgs, methodContext, methodInfo.parameters);
570
575
  return new Promise((succeed, fail) => {
576
+ var _a;
571
577
  const cbid = this._makecbid();
572
578
  this._debug('adding callback to queue', cbid);
573
- this.cbs[cbid] = {
579
+ this.cbs.set(cbid, {
574
580
  objref,
575
581
  override,
576
582
  args,
577
- expectedReturnType: methodInfo.returns ?? 'void',
583
+ expectedReturnType: (_a = methodInfo.returns) !== null && _a !== void 0 ? _a : 'void',
578
584
  succeed,
579
585
  fail,
580
- };
586
+ });
581
587
  });
582
588
  },
583
589
  });
@@ -589,6 +595,7 @@ class Kernel {
589
595
  configurable: false,
590
596
  writable: false,
591
597
  value: (...methodArgs) => {
598
+ var _a;
592
599
  this._debug('invoke sync method override', override, 'args', methodArgs);
593
600
  // We should be validating the actual arguments according to the
594
601
  // declared parameters here, but let's just assume the JSII runtime on the
@@ -599,11 +606,11 @@ class Kernel {
599
606
  invoke: {
600
607
  objref,
601
608
  method: methodName,
602
- args: this._fromSandboxValues(methodArgs, methodInfo.parameters),
609
+ args: this._fromSandboxValues(methodArgs, methodContext, methodInfo.parameters),
603
610
  },
604
611
  });
605
612
  this._debug('Result', result);
606
- return this._toSandbox(result, methodInfo.returns ?? 'void');
613
+ return this._toSandbox(result, (_a = methodInfo.returns) !== null && _a !== void 0 ? _a : 'void', `returned by callback method ${methodName}`);
607
614
  },
608
615
  });
609
616
  }
@@ -629,7 +636,8 @@ class Kernel {
629
636
  return { ti, obj: instance, fn };
630
637
  }
631
638
  _validateMethodArguments(method, args) {
632
- const params = method?.parameters ?? [];
639
+ var _a;
640
+ const params = (_a = method === null || method === void 0 ? void 0 : method.parameters) !== null && _a !== void 0 ? _a : [];
633
641
  // error if args > params
634
642
  if (args.length > params.length && !(method && method.variadic)) {
635
643
  throw new Error(`Too many arguments (method accepts ${params.length} parameters, got ${args.length} arguments)`);
@@ -653,7 +661,7 @@ class Kernel {
653
661
  }
654
662
  }
655
663
  _assemblyFor(assemblyName) {
656
- const assembly = this.assemblies[assemblyName];
664
+ const assembly = this.assemblies.get(assemblyName);
657
665
  if (!assembly) {
658
666
  throw new Error(`Could not find assembly: ${assemblyName}`);
659
667
  }
@@ -676,13 +684,14 @@ class Kernel {
676
684
  return curr;
677
685
  }
678
686
  _typeInfoForFqn(fqn) {
687
+ var _a;
679
688
  const components = fqn.split('.');
680
689
  const moduleName = components[0];
681
- const assembly = this.assemblies[moduleName];
690
+ const assembly = this.assemblies.get(moduleName);
682
691
  if (!assembly) {
683
692
  throw new Error(`Module '${moduleName}' not found`);
684
693
  }
685
- const types = assembly.metadata.types ?? {};
694
+ const types = (_a = assembly.metadata.types) !== null && _a !== void 0 ? _a : {};
686
695
  const fqnInfo = types[fqn];
687
696
  if (!fqnInfo) {
688
697
  throw new Error(`Type '${fqn}' not found`);
@@ -700,12 +709,13 @@ class Kernel {
700
709
  return ti;
701
710
  }
702
711
  _tryTypeInfoForMethod(methodName, classFqn, interfaces = []) {
712
+ var _a, _b;
703
713
  for (const fqn of [classFqn, ...interfaces]) {
704
714
  if (fqn === wire.EMPTY_OBJECT_FQN) {
705
715
  continue;
706
716
  }
707
717
  const typeinfo = this._typeInfoForFqn(fqn);
708
- const methods = typeinfo.methods ?? [];
718
+ const methods = (_a = typeinfo.methods) !== null && _a !== void 0 ? _a : [];
709
719
  for (const m of methods) {
710
720
  if (m.name === methodName) {
711
721
  return m;
@@ -714,7 +724,7 @@ class Kernel {
714
724
  // recursion to parent type (if exists)
715
725
  const bases = [
716
726
  typeinfo.base,
717
- ...(typeinfo.interfaces ?? []),
727
+ ...((_b = typeinfo.interfaces) !== null && _b !== void 0 ? _b : []),
718
728
  ];
719
729
  for (const base of bases) {
720
730
  if (!base) {
@@ -729,6 +739,7 @@ class Kernel {
729
739
  return undefined;
730
740
  }
731
741
  _tryTypeInfoForProperty(property, classFqn, interfaces = []) {
742
+ var _a;
732
743
  for (const fqn of [classFqn, ...interfaces]) {
733
744
  if (fqn === wire.EMPTY_OBJECT_FQN) {
734
745
  continue;
@@ -744,12 +755,12 @@ class Kernel {
744
755
  else if (spec.isInterfaceType(typeInfo)) {
745
756
  const interfaceTypeInfo = typeInfo;
746
757
  properties = interfaceTypeInfo.properties;
747
- bases = interfaceTypeInfo.interfaces ?? [];
758
+ bases = (_a = interfaceTypeInfo.interfaces) !== null && _a !== void 0 ? _a : [];
748
759
  }
749
760
  else {
750
761
  throw new Error(`Type of kind ${typeInfo.kind} does not have properties`);
751
762
  }
752
- for (const p of properties ?? []) {
763
+ for (const p of properties !== null && properties !== void 0 ? properties : []) {
753
764
  if (p.name === property) {
754
765
  return p;
755
766
  }
@@ -774,73 +785,40 @@ class Kernel {
774
785
  }
775
786
  return typeInfo;
776
787
  }
777
- _toSandbox(v, expectedType) {
778
- const serTypes = wire.serializationType(expectedType, this._typeInfoForFqn.bind(this));
779
- this._debug('toSandbox', v, JSON.stringify(serTypes));
780
- const host = {
788
+ _toSandbox(v, expectedType, context) {
789
+ return wire.process({
781
790
  objects: this.objects,
782
791
  debug: this._debug.bind(this),
783
792
  findSymbol: this._findSymbol.bind(this),
784
793
  lookupType: this._typeInfoForFqn.bind(this),
785
- recurse: this._toSandbox.bind(this),
786
- };
787
- const errors = new Array();
788
- for (const { serializationClass, typeRef } of serTypes) {
789
- try {
790
- return wire.SERIALIZERS[serializationClass].deserialize(v, typeRef, host);
791
- }
792
- catch (e) {
793
- // If no union (99% case), rethrow immediately to preserve stack trace
794
- if (serTypes.length === 1) {
795
- throw e;
796
- }
797
- errors.push(e.message);
798
- }
799
- }
800
- throw new Error(`Value did not match any type in union: ${errors.join(', ')}`);
794
+ }, 'deserialize', v, expectedType, context);
801
795
  }
802
- _fromSandbox(v, targetType) {
803
- const serTypes = wire.serializationType(targetType, this._typeInfoForFqn.bind(this));
804
- this._debug('fromSandbox', v, JSON.stringify(serTypes));
805
- const host = {
796
+ _fromSandbox(v, targetType, context) {
797
+ return wire.process({
806
798
  objects: this.objects,
807
799
  debug: this._debug.bind(this),
808
800
  findSymbol: this._findSymbol.bind(this),
809
801
  lookupType: this._typeInfoForFqn.bind(this),
810
- recurse: this._fromSandbox.bind(this),
811
- };
812
- const errors = new Array();
813
- for (const { serializationClass, typeRef } of serTypes) {
814
- try {
815
- return wire.SERIALIZERS[serializationClass].serialize(v, typeRef, host);
816
- }
817
- catch (e) {
818
- // If no union (99% case), rethrow immediately to preserve stack trace
819
- if (serTypes.length === 1) {
820
- throw e;
821
- }
822
- errors.push(e.message);
823
- }
824
- }
825
- throw new Error(`Value did not match any type in union: ${errors.join(', ')}`);
802
+ }, 'serialize', v, targetType, context);
826
803
  }
827
- _toSandboxValues(xs, parameters) {
828
- return this._boxUnboxParameters(xs, parameters, this._toSandbox.bind(this));
804
+ _toSandboxValues(xs, methodContext, parameters) {
805
+ return this._boxUnboxParameters(xs, methodContext, parameters, this._toSandbox.bind(this));
829
806
  }
830
- _fromSandboxValues(xs, parameters) {
831
- return this._boxUnboxParameters(xs, parameters, this._fromSandbox.bind(this));
807
+ _fromSandboxValues(xs, methodContext, parameters) {
808
+ return this._boxUnboxParameters(xs, methodContext, parameters, this._fromSandbox.bind(this));
832
809
  }
833
- _boxUnboxParameters(xs, parameters, boxUnbox) {
834
- parameters = [...(parameters ?? [])];
835
- const variadic = parameters.length > 0 && !!parameters[parameters.length - 1].variadic;
810
+ _boxUnboxParameters(xs, methodContext, parameters = [], boxUnbox) {
811
+ const parametersCopy = [...parameters];
812
+ const variadic = parametersCopy.length > 0 &&
813
+ !!parametersCopy[parametersCopy.length - 1].variadic;
836
814
  // Repeat the last (variadic) type to match the number of actual arguments
837
- while (variadic && parameters.length < xs.length) {
838
- parameters.push(parameters[parameters.length - 1]);
815
+ while (variadic && parametersCopy.length < xs.length) {
816
+ parametersCopy.push(parametersCopy[parametersCopy.length - 1]);
839
817
  }
840
- if (xs.length > parameters.length) {
841
- throw new Error(`Argument list (${JSON.stringify(xs)}) not same size as expected argument list (length ${parameters.length})`);
818
+ if (xs.length > parametersCopy.length) {
819
+ throw new Error(`Argument list (${JSON.stringify(xs)}) not same size as expected argument list (length ${parametersCopy.length})`);
842
820
  }
843
- return xs.map((x, i) => boxUnbox(x, parameters[i]));
821
+ return xs.map((x, i) => boxUnbox(x, parametersCopy[i], `passed to parameter ${parametersCopy[i].name} of ${methodContext}`));
844
822
  }
845
823
  _debug(...args) {
846
824
  if (this.traceEnabled) {
@@ -876,23 +854,6 @@ class Kernel {
876
854
  _makeprid() {
877
855
  return `jsii::promise::${this.nextid++}`;
878
856
  }
879
- _wrapSandboxCode(fn) {
880
- return fn();
881
- }
882
- /**
883
- * Executes arbitrary code in a VM sandbox.
884
- *
885
- * @param code JavaScript code to be executed in the VM
886
- * @param sandbox a VM context to use for running the code
887
- * @param sourceMaps source maps to be used in case an exception is thrown
888
- * @param filename the file name to use for the executed code
889
- *
890
- * @returns the result of evaluating the code
891
- */
892
- _execute(code, filename) {
893
- const script = new vm.Script(code, { filename });
894
- return script.runInContext(this.sandbox, { displayErrors: true });
895
- }
896
857
  }
897
858
  exports.Kernel = Kernel;
898
859
  class Assembly {
package/lib/objects.d.ts CHANGED
@@ -26,7 +26,7 @@ export declare function tagJsiiConstructor(constructor: any, fqn: string): void;
26
26
  */
27
27
  export declare class ObjectTable {
28
28
  private readonly resolveType;
29
- private objects;
29
+ private readonly objects;
30
30
  private nextid;
31
31
  constructor(resolveType: (fqn: string) => spec.Type);
32
32
  /**
@@ -42,7 +42,7 @@ export declare class ObjectTable {
42
42
  /**
43
43
  * Delete the registration with the given objref
44
44
  */
45
- deleteObject(objref: api.ObjRef): void;
45
+ deleteObject({ [api.TOKEN_REF]: objid }: api.ObjRef): void;
46
46
  get count(): number;
47
47
  private makeId;
48
48
  private removeRedundant;