Babel入门指北

5/10/2021 Babel

# 序言

Babel是JavaScript的编译器,主要用于转换ECMAScript 2015+ 的代码,使之可以在各种环境正常运行。用户完全可以使用最新的ECMAScript语法而完全无需担心浏览器是否支持的问题。

# 使用指南

按照惯例,这里依旧采取一个简单的案例来帮助我们更好的理解和使用Babel。

案例主要介绍如何通过Babel的命令行工具转换EMCAScript 2015+的语法至更低的等级。

首先是Babel的安装

npm install --save-dev @babel/core @babel/cli @babel/preset-env
1

创建Babel的配置文件,babel.config.json

{
  "presets": [
    [
      "@babel/env",
      {
        "targets": {
          "edge": "17",
          "firefox": "60",
          "chrome": "67",
          "safari": "11.1"
        },
        "useBuiltIns": "usage", // 当此参数设置为 "usage" 时,就会加载上面所提到的最后一个优化措施,也就是只包含你所需要的 polyfill。
        "corejs": "3.6.5"
      }
    ]
  ]
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17

现在新建一个srclib目录,并在src目录下新建一个main.js文件,内容如下:

const x = (x, y) => x * y
1

通过npx执行babel命令,将src下的文件进行转化并输出到lib目录

npx babel src --out-dir lib --presets=@babel/env
1

现在你可以打开lib目录,查看转换之后的代码了。

# 基础概念

虽然案例看起来十分简单易用,但是了解一些基础概念会让你更好理解Babel。

在上述案例中,我们安装了@babel/core @babel/cli @babel/preset-env这三个包。

其中core是核心,cli是命令行工具(没有cli就需要使用api进行转换),这两个都很好理解,关键是preset-env是什么?

预设preset)是一些插件的集合,@babel/preset-env是个官方的预设,它已经自动帮我们配置了许多插件。例如箭头函数转换。

在没有预设的情况下,你需要自己安装很多插件。

你可以分享自己的插件集合为预设。

Polyfill@babel/polyfill 模块包含 core-js 和一个自定义的 regenerator runtime 来模拟完整的 ES2015+ 环境。

Babel默认只转换语法(syntax),而不转换API,所以需要polyfill来让浏览器支持API,而不是出现xxx is not a function。

这意味着你可以使用诸如 PromiseWeakMap 之类的新的内置组件、 Array.fromObject.assign 之类的静态方法、 Array.prototype.includes 之类的实例方法以及生成器函数(generator functions)(前提是你使用了 regenerator 插件)。

对于一些人来说,可能不会使用到这么多特性,所以preset-env提供了一个参数useBuiltIns,当此参数设置为 usage 时,Babel 将检查你的所有代码,以便查找目标环境中缺失的功能,然后只把必须的 polyfill 包含进来。

从 Babel 7.4.0 版本开始,这个软件包已经不建议使用了,建议直接包含 core-js/stable (用于模拟 ECMAScript 的功能)和 regenerator-runtime/runtime 需要使用转译后的生成器函数):

想了解更多preset可以查看https://babeljs.io/docs/en/babel-preset-env (opens new window)

# webpack & babel

以下是webpack使用babel的指南。

安装loader

npm install --save-dev babel-loader @babel/core
1

安装预设

npm install @babel/preset-env --save-dev
1

webpack.config.js

{
  module: {
    rules: [
      {
        test: /\.m?js$/,
        exclude: /node_modules/,
        use: {
          loader: "babel-loader",
          options: {
            presets: ['@babel/preset-env']
          }
        }
      }
    ]
  }
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16

For more information see the babel/babel-loader repo (opens new window).

babel.config.json

    const path = require('path');

    module.exports = {
      entry: './src/index.js',
      output: {
        filename: 'main.js',
        path: path.resolve(__dirname, 'dist'),
      },
      mode: 'development',
      module: {
+        rules: [
+          {
+            test: /\.m?js$/,
+            exclude: /node_modules/,
+            use: {
+              loader: "babel-loader",
+              options: {
+                presets: ['@babel/preset-env'
+                ]
+              }
+            }
+          }
+        ]
      }
    };
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25

babel.config.json

{
  "presets": ["@babel/preset-env"]
}
1
2
3

# 最后

更多细节参考官方文档 (opens new window)