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
fix: babel-register transform internal dependencies #12665
fix: babel-register transform internal dependencies #12665
Conversation
Build successful! You can test your changes in the REPL here: https://babeljs.io/repl/build/37944/ |
This pull request is automatically built and testable in CodeSandbox. To see build info of the built libraries, click here or the icon next to each commit SHA. Latest deployment of this branch, based on commit a438bf4:
|
Not sure why the last two CircleCI jobs have stalled. |
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.
Thanks!
Don't worry, we only run them manually when needed |
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.
Thanks! I don't really like having to do this, but I can see why it's needed and the solution seems solid.
In the future, when adding ESM support for @babel/register
, I'd like to experiment with moving it to a Worker and it will hopefully also properly solve this.
Thanks very much for merging this so swiftly. Yes, it's a pretty ugly solution, but I couldn't see a better one. If babel-register was implemented as a Node ESM loader then the compilation code would execute in a separate context, so they wouldn't be sharing the same module cache, and this problem would disappear. However, an annoyance with the ESM loaders spec at present is, according to the docs, "When hooks are used they only apply to ES module loading and not to any CommonJS modules loaded." So to support both ESM and CJS, as far as I can see, you'd need two separate babel-register implementations, and it could get messy where an ESM module imports CommonJS and vice-versa. I've been meaning to raise this as an issue on NodeJS but not got around to it yet. |
Have just opened a small follow-up PR #12674 with a slight tweak to implementation. |
If you end up opening it please ping me! I have been privately asking to Node.js maintainers if it's possible do use a single implementation for CJS and ESM, because it would greatly simplify our implementation. |
As discussed in issues #11964 and #12662, babel-register fails to transform modules which Babel uses internally. In a few cases (e.g.
require('to-fast-properties')
), this can cause babel-register to throw an error.These issues arise when babel-register is called with
ignore: []
option so it transforms the contents ofnode_modules
.There are two reasons why modules don't get transformed:
require()
-ed within babel-register before the pirates hook is activated.This PR fixes both problems.
Prior to loading
lib/node.js
, it creates a mock module cache. Allrequire()
calls within babel register use this internal module cache, so untransformed modules are not populated in the global (normal) module cache. When these modules are loaded externally, they pass through register's transform.Usually, messing around with Node's module cache would be considered pretty hacky, but in the context of babel-register, it seems more reasonable to me.
There is a special case for
source-map-support
package which is shared between both the global module cache and register's internal module cache. This is necessary as the module is stateful. It would be ideal to transform this module too, but the workaround necessary to do so is pretty tortuous, so I've omitted it from this PR.