Skip to content

Commit 2e2a848

Browse files
doc,module: clarify hook chain execution sequence
PR-URL: #51884 Reviewed-By: Luigi Pinca <[email protected]> Reviewed-By: Geoffrey Booth <[email protected]>
1 parent 5c97f41 commit 2e2a848

File tree

1 file changed

+18
-14
lines changed

1 file changed

+18
-14
lines changed

doc/api/module.md

Lines changed: 18 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -274,8 +274,8 @@ It's possible to call `register` more than once:
274274
// entrypoint.mjs
275275
import { register } from 'node:module';
276276

277-
register('./first.mjs', import.meta.url);
278-
register('./second.mjs', import.meta.url);
277+
register('./foo.mjs', import.meta.url);
278+
register('./bar.mjs', import.meta.url);
279279
await import('./my-app.mjs');
280280
```
281281
@@ -285,20 +285,23 @@ const { register } = require('node:module');
285285
const { pathToFileURL } = require('node:url');
286286

287287
const parentURL = pathToFileURL(__filename);
288-
register('./first.mjs', parentURL);
289-
register('./second.mjs', parentURL);
288+
register('./foo.mjs', parentURL);
289+
register('./bar.mjs', parentURL);
290290
import('./my-app.mjs');
291291
```
292292
293-
In this example, the registered hooks will form chains. If both `first.mjs` and
294-
`second.mjs` define a `resolve` hook, both will be called, in the order they
295-
were registered. The same applies to all the other hooks.
293+
In this example, the registered hooks will form chains. These chains run
294+
last-in, first out (LIFO). If both `foo.mjs` and `bar.mjs` define a `resolve`
295+
hook, they will be called like so (note the right-to-left):
296+
node's default ← `./foo.mjs``./bar.mjs`
297+
(starting with `./bar.mjs`, then `./foo.mjs`, then the Node.js default).
298+
The same applies to all the other hooks.
296299
297300
The registered hooks also affect `register` itself. In this example,
298-
`second.mjs` will be resolved and loaded per the hooks registered by
299-
`first.mjs`. This allows for things like writing hooks in non-JavaScript
300-
languages, so long as an earlier registered loader is one that transpiles into
301-
JavaScript.
301+
`bar.mjs` will be resolved and loaded via the hooks registered by `foo.mjs`
302+
(because `foo`'s hooks will have already been added to the chain). This allows
303+
for things like writing hooks in non-JavaScript languages, so long as
304+
earlier registered hooks transpile into JavaScript.
302305
303306
The `register` method cannot be called from within the module that defines the
304307
hooks.
@@ -373,11 +376,11 @@ export async function load(url, context, nextLoad) {
373376
}
374377
```
375378
376-
Hooks are part of a chain, even if that chain consists of only one custom
377-
(user-provided) hook and the default hook, which is always present. Hook
379+
Hooks are part of a [chain][], even if that chain consists of only one
380+
custom (user-provided) hook and the default hook, which is always present. Hook
378381
functions nest: each one must always return a plain object, and chaining happens
379382
as a result of each function calling `next<hookName>()`, which is a reference to
380-
the subsequent loader's hook.
383+
the subsequent loader's hook (in LIFO order).
381384
382385
A hook that returns a value lacking a required property triggers an exception. A
383386
hook that returns without calling `next<hookName>()` _and_ without returning
@@ -1060,6 +1063,7 @@ returned object contains the following keys:
10601063
[`register`]: #moduleregisterspecifier-parenturl-options
10611064
[`string`]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/String
10621065
[`util.TextDecoder`]: util.md#class-utiltextdecoder
1066+
[chain]: #chaining
10631067
[hooks]: #customization-hooks
10641068
[load hook]: #loadurl-context-nextload
10651069
[module wrapper]: modules.md#the-module-wrapper

0 commit comments

Comments
 (0)