Skip to content

Commit 6dd0383

Browse files
committed
module: defer ESM bootstrap in pre-execution
1 parent 4dc0d20 commit 6dd0383

File tree

2 files changed

+63
-14
lines changed

2 files changed

+63
-14
lines changed

lib/internal/modules/esm/utils.js

Lines changed: 32 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,9 @@ let defaultConditions;
5353
* @returns {object}
5454
*/
5555
function getDefaultConditions() {
56-
assert(defaultConditions !== undefined);
56+
if (defaultConditions === undefined) {
57+
initializeDefaultConditions();
58+
}
5759
return defaultConditions;
5860
}
5961

@@ -64,7 +66,9 @@ let defaultConditionsSet;
6466
* @returns {Set<any>}
6567
*/
6668
function getDefaultConditionsSet() {
67-
assert(defaultConditionsSet !== undefined);
69+
if (defaultConditionsSet === undefined) {
70+
initializeDefaultConditions();
71+
}
6872
return defaultConditionsSet;
6973
}
7074

@@ -74,18 +78,27 @@ function getDefaultConditionsSet() {
7478
* @returns {void}
7579
*/
7680
function initializeDefaultConditions() {
81+
if (defaultConditions !== undefined) {
82+
return;
83+
}
7784
const userConditions = getOptionValue('--conditions');
7885
const noAddons = getOptionValue('--no-addons');
79-
const addonConditions = noAddons ? [] : ['node-addons'];
80-
const moduleConditions = getOptionValue('--require-module') ? ['module-sync'] : [];
81-
defaultConditions = ObjectFreeze([
82-
'node',
83-
'import',
84-
...moduleConditions,
85-
...addonConditions,
86-
...userConditions,
87-
]);
88-
defaultConditionsSet = new SafeSet(defaultConditions);
86+
const conditions = ['node', 'import'];
87+
if (getOptionValue('--require-module')) {
88+
conditions[conditions.length] = 'module-sync';
89+
}
90+
if (!noAddons) {
91+
conditions[conditions.length] = 'node-addons';
92+
}
93+
for (let i = 0; i < userConditions.length; i++) {
94+
conditions[conditions.length] = userConditions[i];
95+
}
96+
defaultConditions = ObjectFreeze(conditions);
97+
const set = new SafeSet();
98+
for (let i = 0; i < defaultConditions.length; i++) {
99+
set.add(defaultConditions[i]);
100+
}
101+
defaultConditionsSet = set;
89102
}
90103

91104
/**
@@ -295,12 +308,17 @@ async function importModuleDynamicallyCallback(referrerSymbol, specifier, phase,
295308
}
296309

297310
let _shouldSpawnLoaderHookWorker = true;
311+
let esmInitialized = false;
298312
/**
299313
* Initializes handling of ES modules.
300314
* @param {boolean} [shouldSpawnLoaderHookWorker] Whether the custom loader worker
301315
* should be spawned later.
302316
*/
303317
function initializeESM(shouldSpawnLoaderHookWorker = true) {
318+
if (esmInitialized) {
319+
return;
320+
}
321+
esmInitialized = true;
304322
_shouldSpawnLoaderHookWorker = shouldSpawnLoaderHookWorker;
305323
initializeDefaultConditions();
306324
// Setup per-realm callbacks that locate data or callbacks that we keep
@@ -391,6 +409,8 @@ module.exports = {
391409
embedder_module_hdo,
392410
registerModule,
393411
initializeESM,
412+
initializeImportMetaObject,
413+
importModuleDynamicallyCallback,
394414
getDefaultConditions,
395415
getConditionsSet,
396416
shouldSpawnLoaderHookWorker,

lib/internal/process/pre_execution.js

Lines changed: 31 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ const {
1212
NumberParseInt,
1313
ObjectDefineProperty,
1414
ObjectFreeze,
15+
ReflectApply,
1516
String,
1617
globalThis,
1718
} = primordials;
@@ -217,8 +218,36 @@ function initializeModuleLoaders(options) {
217218
// Initialize the ESM loader and a few module callbacks.
218219
// If shouldSpawnLoaderHookWorker is true, later when the ESM loader is instantiated on-demand,
219220
// it will spawn a loader worker thread to handle async custom loader hooks.
220-
const { initializeESM } = require('internal/modules/esm/utils');
221-
initializeESM(shouldSpawnLoaderHookWorker);
221+
if (!shouldSpawnLoaderHookWorker) {
222+
const { initializeESM } = require('internal/modules/esm/utils');
223+
initializeESM(shouldSpawnLoaderHookWorker);
224+
} else {
225+
const {
226+
setImportModuleDynamicallyCallback,
227+
setInitializeImportMetaObjectCallback,
228+
} = internalBinding('module_wrap');
229+
let esmInitialized = false;
230+
let importModuleDynamicallyCallback;
231+
let initializeImportMetaObject;
232+
const ensureEsmInitialized = () => {
233+
if (esmInitialized) return;
234+
const esmUtils = require('internal/modules/esm/utils');
235+
esmUtils.initializeESM(shouldSpawnLoaderHookWorker);
236+
importModuleDynamicallyCallback = esmUtils.importModuleDynamicallyCallback;
237+
initializeImportMetaObject = esmUtils.initializeImportMetaObject;
238+
esmInitialized = true;
239+
};
240+
241+
setImportModuleDynamicallyCallback(function() {
242+
ensureEsmInitialized();
243+
return ReflectApply(importModuleDynamicallyCallback, this, arguments);
244+
});
245+
246+
setInitializeImportMetaObjectCallback(function() {
247+
ensureEsmInitialized();
248+
return ReflectApply(initializeImportMetaObject, this, arguments);
249+
});
250+
}
222251

223252
const {
224253
hasStartedUserCJSExecution,

0 commit comments

Comments
 (0)