-
Notifications
You must be signed in to change notification settings - Fork 29.6k
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
module: add createRequireFunction method #19360
Conversation
doc/api/modules.md
Outdated
|
||
<!-- YAML | ||
added: REPLACEME | ||
--> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should go directly below the heading
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
lol i have no idea how this got down here, will fix
doc/api/modules.md
Outdated
@@ -850,6 +850,21 @@ by the [module wrapper][]. To access it, require the `Module` module: | |||
const builtin = require('module').builtinModules; | |||
``` | |||
|
|||
### module.makeRequire(filename) | |||
|
|||
* `filename` {string|[URL][]} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No need to link here, the type parser should pick URL
up automatically
doc/api/modules.md
Outdated
### module.makeRequire(filename) | ||
|
||
* `filename` {string|[URL][]} | ||
* Returns: {[require][]} Require function |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Code backticks for require
?
lib/module.js
Outdated
m.filename = filename; | ||
m.paths = Module._nodeModulePaths(path.dirname(filename)); | ||
const require = internalModule.makeRequireFunction(m); | ||
return require; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Tiny nit: You could just return
on the previous line :)
const Module = require('module'); | ||
|
||
const p = path.resolve(__dirname, '..', 'fixtures', 'fake.js'); | ||
const req = Module.makeRequire(p); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe also test the URL functionality?
7a0ccd0
to
915a294
Compare
doc/api/modules.md
Outdated
```js | ||
// create a require function which will resolve relative | ||
// to the current ES Module file | ||
const require = module.makeRequire(new URL(import.meta.url)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
module
-> require('module')
?
(in sync with the example above and to not mix with module instances)
doc/api/modules.md
Outdated
--> | ||
|
||
* `filename` {string|URL} Filename for relative importing | ||
* Returns: {[`require`][]} Require function |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe it would be more consistent with other cases to add this to type parser between other Node.js "types". But I am not sure if we should do this for all solitary cases.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
worth a separate pr? (also yay for them all being slightly different)
doc/api/modules.md
873:[`require`]: #modules_require
doc/api/addons.md
1177:[require]: modules.html#modules_require
doc/api/globals.md
168:[`require()`]: modules.html#modules_require
doc/api/modules.md
Outdated
@@ -859,3 +874,4 @@ const builtin = require('module').builtinModules; | |||
[module resolution]: #modules_all_together | |||
[module wrapper]: #modules_the_module_wrapper | |||
[native addons]: addons.html | |||
[`require`]: #modules_require |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe this better be placed after the [`path.dirname()`]
reference, ASCII-wise.
915a294
to
4927c0f
Compare
doc/api/modules.md
Outdated
// to the current ES Module file | ||
const require = require('module').makeRequire(new URL(import.meta.url)); | ||
``` | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
👆 the code example is clunky because require
doesn't exist in ESM and you're assigning a const
named require
while calling the require
function.
lib/module.js
Outdated
@@ -24,7 +24,8 @@ | |||
const { NativeModule } = require('internal/bootstrap_loaders'); | |||
const util = require('util'); | |||
const { decorateErrorStack } = require('internal/util'); | |||
const { getURLFromFilePath } = require('internal/url'); | |||
const { getURLFromFilePath, getPathFromURL } = require('internal/url'); | |||
const { URL } = require('url'); | |||
const vm = require('vm'); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
👆 URL
is already exposed on the global
now. No need to require it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
internally we still require it in case it's overridden
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah, good catch, yes.
4bd8eb4
to
2780483
Compare
doc/api/modules.md
Outdated
// create a require function which will resolve relative | ||
// to the current ES Module file | ||
import Module from 'module'; | ||
const require = Module.makeRequire(new URL(import.meta.url)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is there a way to support simply passing the url string around? Smoothing that over to just work without having to instantiate the URL constructor for things like this would be nice.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
its done like that to mirror how fs
allows URL
objects, i would rather not diverge from that
What is the use-case for this? |
@vkurchatkin mostly just what the example has, but i've found myself creating require functions twice now for things not related to this (mostly very reflective/hacky stuff) and so i thought it might be useful to just make a utility function |
this could use a few more approvals |
The bar for new APIs should be higher than 'might be useful,' IMO. The price of design mistakes is high. |
@bnoordhuis this is designed to alleviate some issues with cjs and esm interop, it's definitely something that will be useful and used, not just a random feature. if you're worried about design mistakes I encourage that you to review this in depth :) |
Still seems more inconvenient than needed. |
CC: @nodejs/modules I'd like to reopen this for discussion in light of some conversation going on in the modules WG nodejs/modules#130 (comment) and the comments leading up to it. In particular, if exposing this is better than shipping It does have the ability for us to create new I'd note that you can create something akin to function makeRequire(filepath) {
const Module = require('module');
const m = new Module(filepath, null);
m._compile('module.exports=require', filepath);
return m.exports;
} I don't think using `m._compile` is problematic in my example and would refrain from that discussion.I took a look at how much `m._compile` corresponds to in the wild usage and I see it used in a variety of places and don't think that it could easily be changed from current the CJS implementation : https://github.com/search?q=_compile+language%3Ajavascript&type=Code , there are false positives but plenty that look to be usage of it from Node's core.In particular, this is an API ergonomics question I think. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
+1 good idea I needed this before and had to use hacks.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I have needed this at various times (mostly for "require relative to project directory"). I'm not sure this is a replacement for import.meta.require
but I think it's a worthwhile feature even from a pure CJS perspective.
fff0660
to
a26ddc0
Compare
require('../common'); | ||
const assert = require('assert'); | ||
const path = require('path'); | ||
const { URL } = require('url'); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
fwiw, URL
should be a global now. There's no reason to require it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
are there any release lines where that hasn't been backported yet?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, it's not on v8.x: #20306
doc/api/modules.md
Outdated
import Module from 'module'; | ||
const require = Module.createRequireFunction(new URL(import.meta.url)); | ||
``` | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Some explanation about why this is useful would probably be a good thing in here. It will be non-obvious to many users and the lack of explanation could lead to confusion.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you also add an example using cjs and require? This is useful outside of ESM.
Notable changes: * fs * Added a `recursive` option to `fs.mkdir` and `fs.mkdirSync`. If this option is set to `true`, non-existing parent folders will be automatically created. #21875 * Fixed fsPromises.readdir `withFileTypes`. #22832 * http2 * Added `http2stream.endAfterHeaders` property. #22843 * module * Added `module.createRequireFromPath(filename)`. This new method can be used to create a custom `require` function that will resolve modules relative to the `filename` path. #19360 * url * Added `url.fileURLToPath(url)` and `url.pathToFileURL(path)`. These methods can be used to correctly convert between `file:` URLs and absolute paths. #22506 * util * Added `util.types.isBoxedPrimitive(value)`. #22620 * Windows * The Windows msi installer now provides an option to automatically install the tools required to build native modules. #22645 * Added new collaborators: * boneskull (https://github.com/boneskull) - Christopher Hiller * The Technical Steering Committee has new members: * apapirovski (https://github.com/apapirovski) - Anatoli Papirovski * gabrielschulhof (https://github.com/gabrielschulhof) - Gabriel Schulhof PR-URL: #22932
PR-URL: #19360 Reviewed-By: Anna Henningsen <anna@addaleax.net> Reviewed-By: Benjamin Gruenbaum <benjamingr@gmail.com> Reviewed-By: Jan Krems <jan.krems@gmail.com> Reviewed-By: Bradley Farias <bradley.meck@gmail.com> Reviewed-By: John-David Dalton <john.david.dalton@gmail.com>
Notable changes: * fs * Added a `recursive` option to `fs.mkdir` and `fs.mkdirSync`. If this option is set to `true`, non-existing parent folders will be automatically created. #21875 * Fixed fsPromises.readdir `withFileTypes`. #22832 * http2 * Added `http2stream.endAfterHeaders` property. #22843 * module * Added `module.createRequireFromPath(filename)`. This new method can be used to create a custom `require` function that will resolve modules relative to the `filename` path. #19360 * url * Added `url.fileURLToPath(url)` and `url.pathToFileURL(path)`. These methods can be used to correctly convert between `file:` URLs and absolute paths. #22506 * util * Added `util.types.isBoxedPrimitive(value)`. #22620 * Added new collaborators: * boneskull (https://github.com/boneskull) - Christopher Hiller * The Technical Steering Committee has new members: * apapirovski (https://github.com/apapirovski) - Anatoli Papirovski * gabrielschulhof (https://github.com/gabrielschulhof) - Gabriel Schulhof PR-URL: #22932
Depends on #21875. Marking |
PR-URL: #19360 Reviewed-By: Anna Henningsen <anna@addaleax.net> Reviewed-By: Benjamin Gruenbaum <benjamingr@gmail.com> Reviewed-By: Jan Krems <jan.krems@gmail.com> Reviewed-By: Bradley Farias <bradley.meck@gmail.com> Reviewed-By: John-David Dalton <john.david.dalton@gmail.com>
Notable changes: * assert * The diff output is now a tiny bit improved by sorting object properties when inspecting the values that are compared with each other. #22788 * cli * The options parser now normalizes `_` to `-` in all multi-word command-line flags, e.g. `--no_warnings` has the same effect as `--no-warnings`. #23020 * Added bash completion for the `node` binary. To generate a bash completion script, run `node --completion-bash`. The output can be saved to a file which can be sourced to enable completion. #20713 * crypto * Added support for PEM-level encryption. #23151 * Added an API asymmetric key pair generation. The new methods `crypto.generateKeyPair` and `crypto.generateKeyPairSync` can be used to generate public and private key pairs. The API supports RSA, DSA and EC and a variety of key encodings (both PEM and DER). #22660 * fs * Added a `recursive` option to `fs.mkdir` and `fs.mkdirSync`. If this option is set to true, non-existing parent folders will be automatically created. #21875 * http2 * Added a `'ping'` event to `Http2Session` that is emitted whenever a non-ack `PING` is received. #23009 * Added support for the `ORIGIN` frame. #22956 * module * Added `module.createRequireFromPath(filename)`. This new method can be used to create a custom require function that will resolve modules relative to the filename path. #19360 * process * Added a `'multipleResolves'` process event that is emitted whenever a `Promise` is attempted to be resolved multiple times, e.g. if the `resolve` and `reject` functions are both called in a `Promise` executor. #22218 * **url** * Added `url.fileURLToPath(url)` and `url.pathToFileURL(path)`. These methods can be used to correctly convert between file: URLs and absolute paths. #22506 * **util** * Added the `sorted` option to `util.inspect()`. If set to `true`, all properties of an object and Set and Map entries will be sorted in the returned string. If set to a function, it is used as a compare function. #22788 * The `util.instpect.custom` symbol is now defined in the global symbol registry as `Symbol.for('nodejs.util.inspect.custom')`. #20857 * **Windows** * The Windows msi installer now provides an option to automatically install the tools required to build native modules. #22645 * **Added new collaborators**: * digitalinfinity - Hitesh Kanwathirtha PR-URL: #23313
Notable changes: * assert * The diff output is now a tiny bit improved by sorting object properties when inspecting the values that are compared with each other. #22788 * cli * The options parser now normalizes `_` to `-` in all multi-word command-line flags, e.g. `--no_warnings` has the same effect as `--no-warnings`. #23020 * Added bash completion for the `node` binary. To generate a bash completion script, run `node --completion-bash`. The output can be saved to a file which can be sourced to enable completion. #20713 * crypto * Added support for PEM-level encryption. #23151 * Added an API asymmetric key pair generation. The new methods `crypto.generateKeyPair` and `crypto.generateKeyPairSync` can be used to generate public and private key pairs. The API supports RSA, DSA and EC and a variety of key encodings (both PEM and DER). #22660 * fs * Added a `recursive` option to `fs.mkdir` and `fs.mkdirSync`. If this option is set to true, non-existing parent folders will be automatically created. #21875 * http2 * Added a `'ping'` event to `Http2Session` that is emitted whenever a non-ack `PING` is received. #23009 * Added support for the `ORIGIN` frame. #22956 * Updated nghttp2 to 1.34.0. This adds RFC 8441 extended connect protocol support to allow use of WebSockets over HTTP/2. #23284 * module * Added `module.createRequireFromPath(filename)`. This new method can be used to create a custom require function that will resolve modules relative to the filename path. #19360 * process * Added a `'multipleResolves'` process event that is emitted whenever a `Promise` is attempted to be resolved multiple times, e.g. if the `resolve` and `reject` functions are both called in a `Promise` executor. #22218 * url * Added `url.fileURLToPath(url)` and `url.pathToFileURL(path)`. These methods can be used to correctly convert between file: URLs and absolute paths. #22506 * util * Added the `sorted` option to `util.inspect()`. If set to `true`, all properties of an object and Set and Map entries will be sorted in the returned string. If set to a function, it is used as a compare function. #22788 * The `util.instpect.custom` symbol is now defined in the global symbol registry as `Symbol.for('nodejs.util.inspect.custom')`. #20857 * Added support for `BigInt` numbers in `util.format()`. #22097 * V8 API * A number of V8 C++ APIs have been marked as deprecated since they have been removed in the upstream repository. Replacement APIs are added where necessary. #23159 * Windows * The Windows msi installer now provides an option to automatically install the tools required to build native modules. #22645 * Workers * Debugging support for Workers using the DevTools protocol has been implemented. #21364 * The public `inspector` module is now enabled in Workers. #22769 * Added new collaborators: * digitalinfinity - Hitesh Kanwathirtha PR-URL: #23313
Notable changes: * assert * The diff output is now a tiny bit improved by sorting object properties when inspecting the values that are compared with each other. #22788 * cli * The options parser now normalizes `_` to `-` in all multi-word command-line flags, e.g. `--no_warnings` has the same effect as `--no-warnings`. #23020 * Added bash completion for the `node` binary. To generate a bash completion script, run `node --completion-bash`. The output can be saved to a file which can be sourced to enable completion. #20713 * crypto * Added support for PEM-level encryption. #23151 * Added an API asymmetric key pair generation. The new methods `crypto.generateKeyPair` and `crypto.generateKeyPairSync` can be used to generate public and private key pairs. The API supports RSA, DSA and EC and a variety of key encodings (both PEM and DER). #22660 * fs * Added a `recursive` option to `fs.mkdir` and `fs.mkdirSync`. If this option is set to true, non-existing parent folders will be automatically created. #21875 * http2 * Added a `'ping'` event to `Http2Session` that is emitted whenever a non-ack `PING` is received. #23009 * Added support for the `ORIGIN` frame. #22956 * Updated nghttp2 to 1.34.0. This adds RFC 8441 extended connect protocol support to allow use of WebSockets over HTTP/2. #23284 * module * Added `module.createRequireFromPath(filename)`. This new method can be used to create a custom require function that will resolve modules relative to the filename path. #19360 * process * Added a `'multipleResolves'` process event that is emitted whenever a `Promise` is attempted to be resolved multiple times, e.g. if the `resolve` and `reject` functions are both called in a `Promise` executor. #22218 * url * Added `url.fileURLToPath(url)` and `url.pathToFileURL(path)`. These methods can be used to correctly convert between file: URLs and absolute paths. #22506 * util * Added the `sorted` option to `util.inspect()`. If set to `true`, all properties of an object and Set and Map entries will be sorted in the returned string. If set to a function, it is used as a compare function. #22788 * The `util.instpect.custom` symbol is now defined in the global symbol registry as `Symbol.for('nodejs.util.inspect.custom')`. #20857 * Added support for `BigInt` numbers in `util.format()`. #22097 * V8 API * A number of V8 C++ APIs have been marked as deprecated since they have been removed in the upstream repository. Replacement APIs are added where necessary. #23159 * Windows * The Windows msi installer now provides an option to automatically install the tools required to build native modules. #22645 * Workers * Debugging support for Workers using the DevTools protocol has been implemented. #21364 * The public `inspector` module is now enabled in Workers. #22769 * Added new collaborators: * digitalinfinity - Hitesh Kanwathirtha PR-URL: #23313
Notable changes: * assert * The diff output is now a tiny bit improved by sorting object properties when inspecting the values that are compared with each other. #22788 * cli * The options parser now normalizes `_` to `-` in all multi-word command-line flags, e.g. `--no_warnings` has the same effect as `--no-warnings`. #23020 * Added bash completion for the `node` binary. To generate a bash completion script, run `node --completion-bash`. The output can be saved to a file which can be sourced to enable completion. #20713 * crypto * Added support for PEM-level encryption. #23151 * Added an API asymmetric key pair generation. The new methods `crypto.generateKeyPair` and `crypto.generateKeyPairSync` can be used to generate public and private key pairs. The API supports RSA, DSA and EC and a variety of key encodings (both PEM and DER). #22660 * fs * Added a `recursive` option to `fs.mkdir` and `fs.mkdirSync`. If this option is set to true, non-existing parent folders will be automatically created. #21875 * http2 * Added a `'ping'` event to `Http2Session` that is emitted whenever a non-ack `PING` is received. #23009 * Added support for the `ORIGIN` frame. #22956 * Updated nghttp2 to 1.34.0. This adds RFC 8441 extended connect protocol support to allow use of WebSockets over HTTP/2. #23284 * module * Added `module.createRequireFromPath(filename)`. This new method can be used to create a custom require function that will resolve modules relative to the filename path. #19360 * process * Added a `'multipleResolves'` process event that is emitted whenever a `Promise` is attempted to be resolved multiple times, e.g. if the `resolve` and `reject` functions are both called in a `Promise` executor. #22218 * url * Added `url.fileURLToPath(url)` and `url.pathToFileURL(path)`. These methods can be used to correctly convert between file: URLs and absolute paths. #22506 * util * Added the `sorted` option to `util.inspect()`. If set to `true`, all properties of an object and Set and Map entries will be sorted in the returned string. If set to a function, it is used as a compare function. #22788 * The `util.instpect.custom` symbol is now defined in the global symbol registry as `Symbol.for('nodejs.util.inspect.custom')`. #20857 * Added support for `BigInt` numbers in `util.format()`. #22097 * V8 API * A number of V8 C++ APIs have been marked as deprecated since they have been removed in the upstream repository. Replacement APIs are added where necessary. #23159 * Windows * The Windows msi installer now provides an option to automatically install the tools required to build native modules. #22645 * Workers * Debugging support for Workers using the DevTools protocol has been implemented. #21364 * The public `inspector` module is now enabled in Workers. #22769 * Added new collaborators: * digitalinfinity - Hitesh Kanwathirtha PR-URL: #23313
Notable changes: * assert * The diff output is now a tiny bit improved by sorting object properties when inspecting the values that are compared with each other. #22788 * cli * The options parser now normalizes `_` to `-` in all multi-word command-line flags, e.g. `--no_warnings` has the same effect as `--no-warnings`. #23020 * Added bash completion for the `node` binary. To generate a bash completion script, run `node --completion-bash`. The output can be saved to a file which can be sourced to enable completion. #20713 * crypto * Added support for PEM-level encryption. #23151 * Added an API asymmetric key pair generation. The new methods `crypto.generateKeyPair` and `crypto.generateKeyPairSync` can be used to generate public and private key pairs. The API supports RSA, DSA and EC and a variety of key encodings (both PEM and DER). #22660 * fs * Added a `recursive` option to `fs.mkdir` and `fs.mkdirSync`. If this option is set to true, non-existing parent folders will be automatically created. #21875 * http2 * Added a `'ping'` event to `Http2Session` that is emitted whenever a non-ack `PING` is received. #23009 * Added support for the `ORIGIN` frame. #22956 * Updated nghttp2 to 1.34.0. This adds RFC 8441 extended connect protocol support to allow use of WebSockets over HTTP/2. #23284 * module * Added `module.createRequireFromPath(filename)`. This new method can be used to create a custom require function that will resolve modules relative to the filename path. #19360 * process * Added a `'multipleResolves'` process event that is emitted whenever a `Promise` is attempted to be resolved multiple times, e.g. if the `resolve` and `reject` functions are both called in a `Promise` executor. #22218 * url * Added `url.fileURLToPath(url)` and `url.pathToFileURL(path)`. These methods can be used to correctly convert between file: URLs and absolute paths. #22506 * util * Added the `sorted` option to `util.inspect()`. If set to `true`, all properties of an object and Set and Map entries will be sorted in the returned string. If set to a function, it is used as a compare function. #22788 * The `util.instpect.custom` symbol is now defined in the global symbol registry as `Symbol.for('nodejs.util.inspect.custom')`. #20857 * Added support for `BigInt` numbers in `util.format()`. #22097 * V8 API * A number of V8 C++ APIs have been marked as deprecated since they have been removed in the upstream repository. Replacement APIs are added where necessary. #23159 * Windows * The Windows msi installer now provides an option to automatically install the tools required to build native modules. #22645 * Workers * Debugging support for Workers using the DevTools protocol has been implemented. #21364 * The public `inspector` module is now enabled in Workers. #22769 * Added new collaborators: * digitalinfinity - Hitesh Kanwathirtha PR-URL: #23313
useful method for all sorts of stuff such as relative require from project root or whatever else you can come up with
Checklist
make -j4 test
(UNIX), orvcbuild test
(Windows) passes