Skip to main content

@babel/register

使用 Babel 的一种方式是通过 require 钩子。require 钩子会将自己绑定到节点的 require 并自动动态编译文件。这相当于 CoffeeScript 的 coffee-script/register

¥One of the ways you can use Babel is through the require hook. The require hook will bind itself to node's require and automatically compile files on the fly. This is equivalent to CoffeeScript's coffee-script/register.

安装

¥Install

npm install @babel/core @babel/register --save-dev

用法

¥Usage

JavaScript
require("@babel/register");

节点所需的所有后续文件扩展名为 .es6.es.jsx.mjs.js 将由 Babel 转换。

¥All subsequent files required by node with the extensions .es6, .es, .jsx, .mjs, and .js will be transformed by Babel.

不包括 Polyfill

在使用需要 polyfill 的功能(如生成器)时,你必须单独包含它。

¥You must include the polyfill separately when using features that require it, like generators.

默认忽略 node_modules

¥Ignores node_modules by default

注意:默认情况下,对 node_modules 的所有引入都将被忽略。你可以通过以下方式传递忽略正则表达式来覆盖它:

¥NOTE: By default all requires to node_modules will be ignored. You can override this by passing an ignore regex via:

JavaScript
require("@babel/register")({
// This will override `node_modules` ignoring - you can alternatively pass
// an array of strings to be explicitly matched or a regex / glob
ignore: [],
});

指定选项

¥Specifying options

JavaScript
require("@babel/register")({
// Array of ignore conditions, either a regex or a function. (Optional)
// File paths that match any condition are not compiled.
ignore: [
// When a file path matches this regex then it is **not** compiled
/regex/,

// The file's path is also passed to any ignore functions. It will
// **not** be compiled if `true` is returned.
function(filepath) {
return filepath !== "/path/to/es6-file.js";
},
],

// Array of accept conditions, either a regex or a function. (Optional)
// File paths that match all conditions are compiled.
only: [
// File paths that **don't** match this regex are not compiled
/my_es6_folder/,

// File paths that **do not** return true are not compiled
function(filepath) {
return filepath === "/path/to/es6-file.js";
},
],

// Setting this will remove the currently hooked extensions of `.es6`, `.es`, `.jsx`, `.mjs`
// and .js so you'll have to add them back if you want them to be used again.
extensions: [".es6", ".es", ".jsx", ".js", ".mjs"],

// Setting this to false will disable the cache.
cache: true,
});

你也可以传入所有其他 选项,包括 pluginspresets。请注意,配置文件 也将被加载,并且程序配置将在文件配置选项之上合并。@babel/register 不支持配置文件中的 ignoreonly

¥You can pass in all other options as well, including plugins and presets. Note that config files will also be loaded and the programmatic config will be merged over top of the file config options. @babel/register does not support ignore and only in config files.

环境变量

¥Environment variables

默认情况下,@babel/node cli 和 @babel/register 将保存到临时目录中的 json 缓存中。

¥By default @babel/node cli and @babel/register will save to a json cache in your temporary directory.

随着文件的启动和编译,这将大大改善。但是,在某些情况下,你希望更改此行为,并且公开了允许你执行此操作的环境变量。

¥This will heavily improve with the startup and compilation of your files. There are however scenarios where you want to change this behaviour and there are environment variables exposed to allow you to do this.

BABEL_CACHE_PATH

指定不同的缓存位置。

¥Specify a different cache location.

Shell
BABEL_CACHE_PATH=/foo/my-cache.json babel-node script.js

BABEL_DISABLE_CACHE

禁用缓存。

¥Disable the cache.

Shell
BABEL_DISABLE_CACHE=1 babel-node script.js

即时编译插件和预设

¥Compiling plugins and presets on the fly

@babel/register 使用 Node 的 require() 钩子系统在加载文件时即时编译文件。虽然这总体上很有帮助,但这意味着可能会出现令人困惑的情况,即 require() 钩子中的代码会导致对 require 的更多调用,从而导致依赖循环。以 Babel 为例,这可能意味着在 Babel 尝试编译用户文件的过程中,Babel 最终可能会在加载时尝试编译自身。

¥@babel/register uses Node's require() hook system to compile files on the fly when they are loaded. While this is quite helpful overall, it means that there can be confusing cases where code within a require() hook causes more calls to require, causing a dependency cycle. In Babel's case for instance, this could mean that in the process of Babel trying to compile a user's file, Babel could end up trying to compile itself as it is loading.

为了避免这个问题,这个模块明确禁止重入编译,例如 Babel 自己的编译逻辑明确不能触发对任何其他文件的进一步编译。这样做的缺点是,如果你想定义一个本身是实时编译的插件或预设,这个过程很复杂。

¥To avoid this problem, this module explicitly disallows re-entrant compilation, e.g. Babel's own compilation logic explicitly cannot trigger further compilation of any other files on the fly. The downside of this is that if you want to define a plugin or preset that is itself live-compiled, the process is complicated.

关键是你自己的代码需要先加载插件/预设。假设插件/预设预先加载其所有依赖,你需要做的是:

¥The crux of it is that your own code needs to load the plugin/preset first. Assuming the plugin/preset loads all of its dependencies up front, what you'll want to do is:

require("@babel/register")({
// ...
});

require("./my-plugin");

因为触发加载的是你自己的代码,而不是 @babel/register 本身的逻辑,所以这应该成功编译任何同步加载的插件/预设。

¥Because it is your own code that triggered the load, and not the logic within @babel/register itself, this should successfully compile any plugin/preset that loads synchronously.

实验性 Babel 8 实现

¥Experimental Babel 8 implementation

你还可以测试将在 Babel 8 中默认启用的新实验性实现,使用

¥You can also test the new experimental implementation that will be enabled by default in Babel 8, using

JavaScript
require("@babel/register/experimental-worker");

它在内部异步运行 Babel,因此它与 .mjs 配置文件 兼容。你已经可以将它用作 @babel/register 的替代品,但需要注意以下几点:

¥It internally runs Babel asynchronously, so it's compatible with .mjs configuration files. You can already use it as a replacement of @babel/register with a few caveats:

  • 如果你以编程方式指定 @babel/register 选项(使用 require("@babel/register")({ /* ... options */ })),则必须确保它们是可序列化的。这意味着你不能传递内联定义的插件函数,但你必须将它们移动到单独的 ./my-plugin.js 文件或 babel.config.js 文件中。

    ¥If you programmatically specify @babel/register options (using require("@babel/register")({ /* ... options */ })), you must make sure that they are serializable. This means that you cannot pass plugin functions defined inline, but you must move them to a separate ./my-plugin.js file or to a babel.config.js file.

  • 新的实现仍然是实验性的:它应该具有与现有功能相同的功能,但可能会有一些新的错误和回归。

    ¥The new implementation is still experimental: it should have the same features as the existing one, but there may be some new bugs and regressions.

注意:@babel/register 不支持动态编译原生 Node.js ES 模块,因为目前没有稳定的 API 来拦截 ES 模块加载。

¥Note: @babel/register does not support compiling native Node.js ES modules on the fly, since currently there is no stable API for intercepting ES modules loading.