Babel 是一个 JavaScript 编译器

Babel 是一个工具链,主要用于将采用 ECMAScript 2015+ 语法编写的代码转换为向后兼容的 JavaScript 语法,以便能够运行在当前和旧版本的浏览器或其他环境中。下面列出的是 Babel 能为你做的事情:

  • 语法转换
  • 通过 Polyfill 方式在目标环境中添加缺失的功能(通过引入第三方 polyfill 模块,例如 core-js
  • 源码转换(codemods)

Babel 和 AST 的关系

  • 核心关系:Babel 通过生成和操作 AST 来实现代码的转换和编译。AST 作为 Babel 处理代码的中间表示,是 Babel 工作流程中不可或缺的一部分。
  • 插件系统:Babel 的强大之处在于其插件系统,这些插件通过分析和修改 AST 来实现具体的语法转换和优化。开发者可以根据需要选择或创建插件,以支持新的语言特性或实现特定的编译任务。

AST 抽象语法树定义 

webpackVite等很多的工具和库的核心都是通过Abstract Syntax Tree抽象语法树这个概念来实现对代码的检查、分析等操作的,这些工具的原理都是通过JavaScript Parser把代码转化为一颗抽象语法树(AST),这颗树定义了代码的结构,通过操纵这颗树,我们可以精准的定位到声明语句、赋值语句、运算语句等等,实现对代码的分析、优化、变更等操作

在计算机科学中,抽象语法树(abstract syntax tree或者缩写为AST),或者语法树(syntax tree),是源代码的抽象语法结构的树状表现形式,这里特指编程语言的源代码。

Javascript的语法是为了给开发者更好的编程而设计的,但是不适合程序的理解。所以需要转化为AST来使之更适合程序分析,浏览器编译器一般会把源码转化为AST来进行进一步的分析等其他操作。

抽象语法树用途 

  • 代码语法的检查、代码风格的检查、代码的格式化、代码的高亮、代码错误提示、代码自动补全等等
    • 如JSLint、JSHint对代码错误或风格的检查,发现一些潜在的错误
    • IDE的错误提示、格式化、高亮、自动补全等等
  • 代码混淆压缩
    • UglifyJS2等
  • 优化变更代码,改变代码结构使达到想要的结构
    • 代码打包工具webpack、rollup等等
    • CommonJS、AMD、CMD、UMD等代码规范之间的转化
    • CoffeeScript、TypeScript、JSX等转化为原生Javascript

3.babel插件

  • 访问者模式Visitor 对于某个对象或者一组对象,不同的访问者,产生的结果不同,执行操作也不同
  • @babel/core Babel 的编译器,核心 API 都在这里面,比如常见的 transform、parse
  • [@babel/parser] Babel 的解析器
  • babel-types 用于 AST 节点的 Lodash 式工具库, 它包含了构造、验证以及变换 AST 节点的方法,对编写处理 AST 逻辑非常有用
  • babel-traverse用于对 AST 的遍历,维护了整棵树的状态,并且负责替换、移除和添加节点
  • babel-types-api
  • Babel 插件手册
  • babeljs.io babel可视化编译器

转换箭头函数 

转换前

 1const sum = (a,b)=>a+b

转换后

 1var sum = function sum(a, b) {
 2  return a + b;
 3};

 1let babel = require('@babel/core');
 2let t = require('babel-types');
 3const code = `const sum = (a,b)=>a+b`;
 4let transformArrowFunctions = {
 5    visitor: {
 6        ArrowFunctionExpression: (path) => {
 7            let node = path.node;
 8            let id = path.parent.id;
 9            let params = node.params;
10            let body=t.blockStatement([
11                t.returnStatement(node.body)
12            ]);
13            let functionExpression = t.functionExpression(id,params,body,false,false);
14            path.replaceWith(functionExpression);
15        }
16    }
17}
18const result = babel.transform(code, {
19    plugins: [transformArrowFunctions]
20});
21console.log(result.code);

Babel 在真实项目中遇到的问题有哪些 ?

 1{
 2  test: /\.js$/, 
 3  exclude: /node_modules/, 
 4  use: {
 5    loader: 'babel-loader', 
 6    options: {
 7      cacheDirectory: true, 
 8      presets: [ 
 9        '@babel/preset-env', 
10        {
11          useBuiltIns: 'usage', 
12          corejs: 3, 
13          targets: { 
14            chrome: '49', 
15          },
16        },
17        '@babel/preset-react', 
18        '@babel/preset-typescript', 
19      ],
20      plugins: [ 
21        '@babel/plugin-proposal-nullish-coalescing-operator', 
22        '@babel/plugin-transform-optional-chaining', 
23      ],
24    },
25  },
26}

个人笔记记录 2021 ~ 2025