babel的开端相识

前段时候最先研讨ast,然后逐步的顺便把babel都研讨了,至于ast稍后的时候会写一篇引见性博客特地引见ast,本博客先引见一下babel的基础知识点。

  • 背景:

由于如今前端涌现了许多非es5的语法,如jsx,.vue,ts等等的花样和写法,假如要在浏览器的装备上辨认并实行,须要分外将这些非传统花样的语法转成传统的es5花样,而babel插件,就是用来将非es5花样的语法转成es5语法。

babel实际上是一个诠释器,它重要讲举行中的代码分为三个阶段实行:诠释,转换,天生。个中babel插件或许其他插件都是在转换阶段起作用。

  • babel中心包:

babel既然是个诠释器,那末就会具有诠释,遍历,以及天生的一系列东西和api:

1)babylon:babel内里用来将js代码词法剖析,天生ast,他的构造有些像acron,它的返回的构造内里包括着ast和tokens。

require("babylon").parse("code", {
  // parse in strict mode and allow module declarations
  sourceType: "module",

  plugins: [
    // enable jsx and flow syntax
    "jsx",
    "flow"
  ]
});

sourceType: module示意的是在严厉情势下剖析而且许可模块定义(即能辨认import和expor语法);script辨认不了。

2)babel-traverse:功用就像estraverse一样,主如果给plugin供应遍历ast节点的功用;

var babylon = require('babylon');
var result = babylon.parse(code, { sourceType: "module",});
console.log('result:', result);

import traverse from "babel-traverse";

traverse(result, {
    enter(node) {
       console.log(node);
    }
});

3)babel-generator:将ast天生js代码;

var babylon = require('babylon');
var result = babylon.parse(code, { sourceType: "module",});
console.log('result:', result);

import traverse from "babel-traverse";
import generate from 'babel-generator';

traverse(result, {
    enter(node) {
       console.log(node);
    }
});

var conde1 = generate(result);
console.log('generate:', conde1);
  • babel东西包:

要完成庞杂的转换事情,单靠中心包是不能完成的,所以必要还要依赖于其他东西包辅佐。

1)babel-types:包括着ast中的一切范例,能够天生一个ast的节点,然后替代真是ast的节点,从而转变ast的内容(ast东西库,类似于lodash,具有校验,创建和转换ast的要领)。

import * as t from "babel-types";

console.log(t.stringLiteral("my-module"));

语法:t.anyTypeAnnotation(内容) // 终究返回一个范例的对象

2)babel-template:能够经由历程字符串的情势天生一个ast;

import template from "babel-template";
const buildRequire = template(`
  var IMPORT_NAME = require(SOURCE);
`);

const ast2 = buildRequire({
    IMPORT_NAME: t.identifier("myModule"),
    SOURCE: t.stringLiteral("my-module")
});

console.log('ast2', ast2);

3)babel-helps: 主如果用来辅佐babel转换;

4)babel-core-frame: 主如果用来将错误信息打印出来;

5)babel-cli:babel的命令行东西,经由历程命令行对js代码举行转译;

6)babel-register: 由于babel东西文件,插件内里运用了许多require,而 该文件能够将node中的require于babel中的require绑定,从而能够运用require引入文件;

7)babel-plugin-xxx: 在转换历程当中运用的插件;

8)babel-plugin-transform-xxx: 在transerform历程当中运用到的插件;

(.babelrc文件:该文件会在babel编译历程当中,自动设置babel的参数,babel的运转环境–env,babel的设置—preset,babel的所须要用到的插件—plugins等)

9)babel-core:该中心包包括着babel的中心(babel-lon,babel-traverse,babel-generate),供应了更多更和睦的api给开辟者运用。

  • babel编译道理:

编译器就是讲高等的言语或许语法,编译成更进阶机械辨认的言语和语法;

babel实在更像一个转译器,由于它主如果将高等的js语法转成初级的语法;

他们二者虽然有区分,但有许多相似之处(都是阅历三个历程:剖析,处置惩罚,天生);

以es6转成es5为例:

ES6代码输入 ==》 babylon举行剖析 ==》 获得AST ==》 plugin用babel-traverse对AST树举行遍历转译 ==》 获得新的AST树 ==》 用babel-generator经由历程AST树天生ES5代码

  • babel-pollfill,babel-runtime,transfer-runtime的区分:

babel-pollfill是针关于运用和页面范围内,对新的对象和新的语法举行兼容,主如果经由历程一些辅佐函数举行兼容新的语法,但假如针对外部的库运用,就会发生污染全局环境的影响,平常对项目代码运用;

babel-runtime是关于外部插件和库的语法兼容,能将新的对象和语法,经由历程在运转时,把对应的可辨认的语法和对象婚配出来并举行转换,从而显现在运转时举行语法降级兼容,且不会发生全局污染,平常对外部的插件运用;

transfer-babel是对babel-runtime举行封装,新的语法,对象能经由历程该插件,换种情势援用runtime的东西;

(实在runtime,pollfill都是建立在core-js之上的)。

关于babel的插件,主如果由于天生的ast的底层中有一个accept要领,特地用来吸收visitor(插件)访问者对象,然后在visitor中定义种种节点范例的操纵-visite,每一个visite都能够接收一个path参数(节点信息,节点和位置信息的对象,其包括许多有效的要领),在visit中处置惩罚path,从而完成转换的作用。

const result = babel.transform(code, {
    plugins: [{
        visitor
    }]
})
console.log(result.code);

至于visitor后续会细致引见。

全部babel的构造图,我也许花了一张图示意出来:

《babel的开端相识》

而babel和webpack的协同开辟,我也也许花了一张图示意他们之间的关联,但内里的道理,我后续会再去研讨,研讨好再分享一下:

《babel的开端相识》

以上是我对babel的开端明白,假如有不正确的处所,迎接指出。

    原文作者:DragonChen
    原文地址: https://segmentfault.com/a/1190000017499449
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞