39
39
40
40
// @ts -check
41
41
/* eslint-disable no-underscore-dangle */
42
- /// <reference types="ses">
43
42
44
43
import {
45
44
Map ,
@@ -68,17 +67,49 @@ import { getDeferredExports } from './module-proxy.js';
68
67
import { compartmentEvaluate } from './compartment-evaluate.js' ;
69
68
import { makeSafeEvaluator } from './make-safe-evaluator.js' ;
70
69
71
- /** @import {ModuleDescriptor, ModuleExportsNamespace} from '../types.js' */
70
+ /**
71
+ * @import {ImportHook, ImportMetaHook, ImportNowHook, ModuleDescriptor, ModuleExportsNamespace, ModuleMap, ModuleMapHook, ResolveHook, ModuleSource, CompartmentOptions} from '../types.js'
72
+ * @import {Transform} from './lockdown.js'
73
+ * @import {DeferredExports} from './module-proxy.js'
74
+ */
72
75
73
- // moduleAliases associates every public module exports namespace with its
74
- // corresponding compartment and specifier so they can be used to link modules
75
- // across compartments.
76
- // The mechanism to thread an alias is to use the compartment.module function
77
- // to obtain the exports namespace of a foreign module and pass it into another
78
- // compartment's moduleMap constructor option.
76
+ /**
77
+ * Associates every public module exports namespace with its corresponding
78
+ * compartment and specifier so they can be used to link modules across
79
+ * compartments. The mechanism to thread an alias is to use the
80
+ * {@link Compartment.module} function to obtain the exports namespace of a foreign
81
+ * module and pass it into another compartment's `moduleMap` constructor option
82
+ * @type {WeakMap<ModuleExportsNamespace, Compartment> }
83
+ *
84
+ */
79
85
const moduleAliases = new WeakMap ( ) ;
80
86
81
- // privateFields captures the private state for each compartment.
87
+ /**
88
+ * Private fields for `Compartment` instances
89
+ * @typedef {object } CompartmentFields
90
+ * @property {string } name
91
+ * @property {object } globalObject
92
+ * @property {Array<Transform> } globalTransforms
93
+ * @property {(source: string, options?: {localTransforms?: Array<Transform>}) => void } safeEvaluate
94
+ * @property {ResolveHook } resolveHook
95
+ * @property {ImportHook } importHook
96
+ * @property {ImportNowHook } importNowHook
97
+ * @property {ModuleMap } moduleMap
98
+ * @property {ModuleMapHook } moduleMapHook
99
+ * @property {ImportMetaHook } importMetaHook
100
+ * @property {Map<string, ModuleSource> } moduleRecords
101
+ * @property {Array<Transform> } __shimTransforms__
102
+ * @property {DeferredExports } deferredExports
103
+ * @property {Map<string, ModuleDescriptor> } instances
104
+ * @property {Compartment } [parentCompartment]
105
+ * @property {boolean } noNamespaceBox
106
+ * @property {(fullSpecifier: string) => Promise<ModuleExportsNamespace> } compartmentImport
107
+ */
108
+
109
+ /**
110
+ * Captures the private state for each {@link Compartment}
111
+ * @type {WeakMap<Compartment, CompartmentFields> }
112
+ */
82
113
const privateFields = new WeakMap ( ) ;
83
114
84
115
export const InertCompartment = function Compartment (
@@ -94,6 +125,7 @@ export const InertCompartment = function Compartment(
94
125
/**
95
126
* @param {Compartment } compartment
96
127
* @param {string } specifier
128
+ * @returns {{namespace: ModuleExportsNamespace} }
97
129
*/
98
130
const compartmentImportNow = ( compartment , specifier ) => {
99
131
const { execute, exportsProxy } = link (
@@ -106,27 +138,20 @@ const compartmentImportNow = (compartment, specifier) => {
106
138
return exportsProxy ;
107
139
} ;
108
140
141
+ /** @type {Compartment & {constructor: typeof InertCompartment} } */
109
142
export const CompartmentPrototype = {
110
143
constructor : InertCompartment ,
111
144
112
145
get globalThis ( ) {
113
- return weakmapGet ( privateFields , this ) . globalObject ;
146
+ return /** @type {CompartmentFields } */ ( weakmapGet ( privateFields , this ) )
147
+ . globalObject ;
114
148
} ,
115
149
116
150
get name ( ) {
117
- return weakmapGet ( privateFields , this ) . name ;
151
+ return /** @type {CompartmentFields } */ ( weakmapGet ( privateFields , this ) )
152
+ . name ;
118
153
} ,
119
154
120
- /**
121
- * @param {string } source is a JavaScript program grammar construction.
122
- * @param {object } [options]
123
- * @param {Array<import('./lockdown-shim').Transform> } [options.transforms]
124
- * @param {boolean } [options.sloppyGlobalsMode]
125
- * @param {object } [options.__moduleShimLexicals__]
126
- * @param {boolean } [options.__evadeHtmlCommentTest__]
127
- * @param {boolean } [options.__evadeImportExpressionTest__]
128
- * @param {boolean } [options.__rejectSomeDirectEvalExpressions__]
129
- */
130
155
evaluate ( source , options = { } ) {
131
156
const compartmentFields = weakmapGet ( privateFields , this ) ;
132
157
return compartmentEvaluate ( compartmentFields , source , options ) ;
@@ -148,7 +173,9 @@ export const CompartmentPrototype = {
148
173
} ,
149
174
150
175
async import ( specifier ) {
151
- const { noNamespaceBox } = weakmapGet ( privateFields , this ) ;
176
+ const { noNamespaceBox } = /** @type {CompartmentFields } */ (
177
+ weakmapGet ( privateFields , this )
178
+ ) ;
152
179
153
180
if ( typeof specifier !== 'string' ) {
154
181
throw TypeError ( 'first argument of import() must be a string' ) ;
@@ -187,7 +214,7 @@ export const CompartmentPrototype = {
187
214
}
188
215
189
216
loadNow ( privateFields , moduleAliases , this , specifier ) ;
190
- return compartmentImportNow ( /** @type { Compartment } */ ( this ) , specifier ) ;
217
+ return compartmentImportNow ( this , specifier ) ;
191
218
} ,
192
219
} ;
193
220
@@ -218,15 +245,35 @@ defineProperties(InertCompartment, {
218
245
* @returns {Compartment['constructor'] }
219
246
*/
220
247
221
- // In order to facilitate migration from the deprecated signature
222
- // of the compartment constructor,
223
- // new Compartent(globals?, modules?, options?)
224
- // to the new signature:
225
- // new Compartment(options?)
226
- // where globals and modules are expressed in the options bag instead of
227
- // positional arguments, this function detects the temporary sigil __options__
228
- // on the first argument and coerces compartments arguments into a single
229
- // compartments object.
248
+ /**
249
+ * "Options bag"-style `Compartment` constructor arguments.
250
+ * @typedef {[options?: CompartmentOptions & { __options__: true }] } CompartmentOptionsArgs
251
+ */
252
+
253
+ /**
254
+ * Legacy `Compartment` constructor arguments.
255
+ *
256
+ * @deprecated
257
+ * @typedef {[globals?: Map<string, any>, modules?: Map<string, ModuleDescriptor>, options?: CompartmentOptions] } LegacyCompartmentOptionsArgs
258
+ */
259
+
260
+ /**
261
+ * In order to facilitate migration from the deprecated signature of the
262
+ * compartment constructor,
263
+ *
264
+ * `new Compartent(globals?, modules?, options?)`
265
+ *
266
+ * to the new signature:
267
+ *
268
+ * `new Compartment(options?)`
269
+ *
270
+ * ...where globals and modules are expressed in the options bag instead of
271
+ * positional arguments, this function detects the temporary sigil __options__
272
+ * on the first argument and coerces compartments arguments into a single
273
+ * compartments object.
274
+ * @param {CompartmentOptionsArgs|LegacyCompartmentOptionsArgs } args
275
+ * @returns {CompartmentOptions }
276
+ */
230
277
export const compartmentOptions = ( ...args ) => {
231
278
if ( args . length === 0 ) {
232
279
return { } ;
@@ -248,7 +295,7 @@ export const compartmentOptions = (...args) => {
248
295
globals = /** @type {Map<string, any> } */ ( { } ) ,
249
296
modules = /** @type {Map<string, ModuleDescriptor> } */ ( { } ) ,
250
297
options = { } ,
251
- ] = args ;
298
+ ] = /** @type { LegacyCompartmentOptionsArgs } */ ( args ) ;
252
299
assertEqual (
253
300
options . modules ,
254
301
undefined ,
@@ -274,6 +321,10 @@ export const makeCompartmentConstructor = (
274
321
markVirtualizedNativeFunction ,
275
322
{ parentCompartment = undefined , enforceNew = false } = { } ,
276
323
) => {
324
+ /**
325
+ *
326
+ * @param {CompartmentOptionsArgs|LegacyCompartmentOptionsArgs } args
327
+ */
277
328
function Compartment ( ...args ) {
278
329
if ( enforceNew && new . target === undefined ) {
279
330
throw TypeError (
0 commit comments