Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

esm: update loaders warning #49633

Merged
merged 7 commits into from
Sep 19, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
30 changes: 26 additions & 4 deletions lib/internal/modules/esm/loader.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,16 @@
require('internal/modules/cjs/loader');

const {
ArrayPrototypeJoin,
ArrayPrototypeMap,
ArrayPrototypeReduce,
FunctionPrototypeCall,
JSONStringify,
ObjectSetPrototypeOf,
RegExpPrototypeSymbolReplace,
SafeWeakMap,
encodeURIComponent,
hardenRegExp,
} = primordials;

const {
Expand Down Expand Up @@ -499,7 +506,7 @@ class CustomizedModuleLoader {
}
}

let emittedExperimentalWarning = false;
let emittedLoaderFlagWarning = false;
/**
* A loader instance is used as the main entry point for loading ES modules. Currently, this is a singleton; there is
* only one used for loading the main module and everything in its dependency graph, though separate instances of this
Expand All @@ -515,9 +522,24 @@ function createModuleLoader(useCustomLoadersIfPresent = true) {
!require('internal/modules/esm/utils').isLoaderWorker()) {
const userLoaderPaths = getOptionValue('--experimental-loader');
if (userLoaderPaths.length > 0) {
if (!emittedExperimentalWarning) {
emitExperimentalWarning('Custom ESM Loaders');
emittedExperimentalWarning = true;
if (!emittedLoaderFlagWarning) {
const readableURIEncode = (string) => ArrayPrototypeReduce(
[
[/'/g, '%27'], // We need to URL-encode the single quote as it's the delimiter for the --import flag.
GeoffreyBooth marked this conversation as resolved.
Show resolved Hide resolved
[/%22/g, '"'], // We can decode the double quotes to improve readability.
[/%2F/ig, '/'], // We can decode the slashes to improve readability.
],
(str, { 0: regex, 1: replacement }) => RegExpPrototypeSymbolReplace(hardenRegExp(regex), str, replacement),
encodeURIComponent(string));
process.emitWarning(
'`--experimental-loader` may be removed in the future; instead use `register()`:\n' +
`--import 'data:text/javascript,import { register } from "node:module"; import { pathToFileURL } from "node:url"; ${ArrayPrototypeJoin(
ArrayPrototypeMap(userLoaderPaths, (loader) => `register(${readableURIEncode(JSONStringify(loader))}, pathToFileURL("./"))`),
guybedford marked this conversation as resolved.
Show resolved Hide resolved
'; ',
)};'`,
'ExperimentalWarning',
);
emittedLoaderFlagWarning = true;
}
customizations = new CustomizedModuleLoader();
}
Expand Down
10 changes: 7 additions & 3 deletions test/es-module/test-esm-experimental-warnings.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -24,14 +24,18 @@ describe('ESM: warn for obsolete hooks provided', { concurrency: true }, () => {

describe('experimental warnings for enabled experimental feature', () => {
for (
const [experiment, arg] of [
[/Custom ESM Loaders/, `--experimental-loader=${fileURL('es-module-loaders', 'hooks-custom.mjs')}`],
const [experiment, ...args] of [
[
/`--experimental-loader` may be removed in the future/,
'--experimental-loader',
fileURL('es-module-loaders', 'hooks-custom.mjs'),
],
[/Network Imports/, '--experimental-network-imports'],
]
) {
it(`should print for ${experiment.toString().replaceAll('/', '')}`, async () => {
const { code, signal, stderr } = await spawnPromisified(execPath, [
arg,
...args,
'--input-type=module',
'--eval',
`import ${JSON.stringify(fileURL('es-module-loaders', 'module-named-exports.mjs'))}`,
Expand Down