Allow preset-env to toggle module handling based on flags from the caller (like babel-loader)#8485
Conversation
|
Build successful! You can test your changes in the REPL here: https://babeljs.io/repl/build/8854/ |
|
Build successful! You can test your changes in the REPL here: https://babeljs.io/repl/build/8829/ |
|
@Andarist Any thoughts on this, since it'll probably fit nicely into your work on the Rollup plugin too. |
| // When the `exclude` callback returns a truthy value, Babel not use the | ||
| // 'item' plugin here. | ||
| overrides.push({ | ||
| exclude: (filename, { caller }) => caller && caller.supportsStaticESM, |
There was a problem hiding this comment.
Since the caller isn't file-specific but it is more similar to env, can we pass it using the api object instead using the exclude option (which is usally used to exclude plugins based on the file path)?
There was a problem hiding this comment.
That's a great question. Let me revisit that. This approach was from an old branch I had, so I hadn't acutally revisited that. My concern would be caching of plugin instances. The issue with caching is that the API would need to be
const supportsStaticESM = api.caller(caller => !!(caller && caller.supportsStaticESM));
because your build might be used both with and without static ESM support, and Babel needs to know whether or not it should re-evaluate the plugin function, since it does its best to only evaluate the plugin/preset functions a single time unless told otherwise.
I'm actually fine if we want to expose the api approach, but I'd still probably be tempted to leave this exposed in test/include/exclude too.
There was a problem hiding this comment.
Caller is an object that can only contain null, undefined, booleans, strings, and numbers: it can be JSON.stringifyed and stored to invalidate the cache when needed.
There was a problem hiding this comment.
That's true, I'm personally not a huge fan of that because we could always want to expand that in the future, and having to re-stringify the object all the time just seems undesirable. At the end of the day I don't feel that strongly about it I guess. One other downside being that the plugin cache would get invalidated if any caller flag changed, even if it was something other than supportsStaticESM.
| export function buildPresetChain( | ||
| arg: PresetInstance, | ||
| context: *, | ||
| ): ConfigChain | null { |
There was a problem hiding this comment.
This function never returns null.
|
Does Babel use the same config validation for config files and options directly passed to |
Already done! |
5e28652 to
a68f3e8
Compare
| moduleTransformations[modules] && | ||
| // TODO: Remove the 'api.caller' check eventually. Just here to prevent | ||
| // unnecessary breakage in the short term for users on older betas/RCs. | ||
| (modules !== "auto" || !api.caller || !api.caller(supportsStaticESM)) |
There was a problem hiding this comment.
@nicolo-ribaudo Thoughts? Ended up exposing both and using the api.caller approach I mentioned.
a68f3e8 to
d60c5e1
Compare
| }); | ||
|
|
||
| it("`false` option returns commonjs", () => { | ||
| it("`false` option returns false", () => { |
|
This is really great! Something we should document for our integrations to also take advantage of. |
|
🚀 super! Sorry I've missed this PR before, but this is super awesome - preventing the users misconfiguring their tool in clean way, gonna land this in rollup-plugin-babel once it gets released |
This resolves a frustrating error I encountered where I was receiving:
ReferenceError: Unknown option: .caller
...when trying to use `@babel/register`. This mysteriously went away when I
upgraded to `rc.2`, which was inspired after I honed in on related work to
the `caller` option in babel/babel#8485 after debugging
Babel's `loadOptions` (in `7.0.0-rc.1`) with the Node.js debugger.
| ` - 'false' to indicate no module processing\n` + | ||
| ` - a specific module type: 'commonjs', 'amd', 'umd', 'systemjs'` + | ||
| ` - 'auto' (default) which will automatically select 'false' if the current\n` + | ||
| ` process is known to support ES module syntax, or "commonjs" otherwise\n`, |
There was a problem hiding this comment.
Hi, I have a ❓ about "if the current process is known to support ES module syntax". I'm not sure what that means. Can someone please clarify? Thank you!
There was a problem hiding this comment.
For example, if you are calling Babel using babel-loader, modules will be set to false because webpack supports ES modules
There was a problem hiding this comment.
Thanks @nicolo-ribaudo, I'll link to your reply from babel/babel-loader#521 😃
What this PR essentially means is that utilities calling Babel can:
For instance,
babel-loaderwould be able to do:and
preset-envcan automatically change its behavior frommodules: "commonjs"tomodules: false.