关于babel,你应该知道的一些事

概要

babel本身是一个工具,负责将es6/es7的代码转换成es5的代码,以便在现代浏览器里面运行,更重要的是,babel的扩展机制使其可以为React转换jsx,为Flow做静态语法分析。

babel由各种小模块组成,它通过预置一些插件来转换代码,我们接下来会谈到。

注意: 假设你本地安装了node和npm,且不排斥使用命令行工具,同时确保你的项目里面包含pajkage.json文件;

babel-cli

Babel CLI通过命令行实现代码的转换,你可以通过 npm install babel-cli -g 全局安装它,当然也可以在本地项目目录下执行 npm install babel-cli –save-dev 实现本地安装,

这里推荐项目本地安装的方式,主要有以下两个优势:

1.不同的项目本身对babel的版本依赖会有所差异,防止强依赖;
2.项目本身依赖的babel版本可以任意自由灵活管控;

项目安装完 babel-cli 依赖之后,你就可以在控制台输入以下指令:

1
babel example.js --out-file compiled.js

指令每部分的含义:

  • babel 调用babel cli;
  • example.js 指定的需要转换的es6/es7文件;
  • –out-file babel 编译选项,代表编译完的文件输出信息,可以简写成 -o,如果需要编译目录文件,则输出项用 –output-dir ,可以简写成 -d;
  • compiled.js - 指定输出的文件名;

每次改完代码都敲一遍指令,显然是件繁琐的事,我们可以通过给package.json的scripts配置一条构建任务指令,实现该步骤的自动化:

1234567
{    ...    "scripts": {        "build": "babel ./src -d ./lib -w"    }    ...}

以上-w指令代表babel会监视src目录下的文件变化,如变化就执行重新编译该代码并输入到lib目录下;

babel-register

babel-register 通过绑定node的require函数,通过钩子函数实现在线代码转换;这种方式不推荐在生产环境使用,由于实时代码转换会带来性能的损耗而导致体验低下,所以更优的方式是代码部署前先完成代码的转换;

不过开发环境使用还是很方便的,可以实现直接编译并执行代码,那如何使用babel-register呢?
首先需要通过以下指令安装 babel-register

1
npm install babel-register --save-dev

创建一个简单es6/es7文件 index.js:

12
const sayHello = () => {console.log('hello')};sayHello();

创建新文件去require index.js文件 register.js:

12
require('babel-register');require('index.js');

当我们运行 node register.js时,控制台会输出 hello;

babel-node

如果想快速的执行一个需babel转换的文件,最好的方式是使用 babel-node 命令, 该方式同样不建议在生产环境使用,理由同上,安装了babel cli天然就携带了babel-node,如何使用呢?

首先 创建一个简单es6/es7文件 index.js:

12
const sayHello = () => {console.log('hello')};sayHello();

接下来直接 babel-node index.js ,接下来就可以在控制台看到 hello 的输出;

Configuring Babel

正如之前所说,如果你不告知babel该做什么,babel本事不会做任何事情,除了将文件从一个地方挪到另一个地方,所以我们必须给babel提供presets和plugins配置来告知babel如何工作。

.babelrc

.babelrc 文件是babel的配置文件,大概的文件结构如下

1234
{    "presets": [],    "plugins": []}

现在假设我们要通过babel的配置文件告知babel将一份基于标准 es6 React的代码转成es5,如何做?

  1. 首先我们需要安装es2015的preset和React的preset;
12
npm install babel-preset-es2015 --save-devnpm install babel-preset-react --save-dev
  1. 更新 .babelrc , 添加preset配置即可;
1234
{    "presets": ["es2015", "react"],    "plugins": []}

那如果我们的代码文件里面用了许多es6草案阶段(Draft)的语法时,babel需要额外添加什么preset呢,众所周知,一个标准的js规范需要经历5个阶段(Strawman, Proposal, Draft, Candidate, Finished),才会最终纳入标准,而草案阶段是很有可能最终纳入标准的, babel通过预置不同阶段的preset完成相应转换工作,主要有以下4个:

  • babel-preset-stage-0
  • babel-preset-stage-1
  • babel-preset-stage-2
  • babel-preset-stage-3

之所以没有 babel-preset-stage-5 , 是因为它就是 babel-preset-es2015

以上每个stage的preset都依赖它后一个preset,例如babel-preset-stage-1依赖于 babel-preset-stage-2 和 babel-preset-stage-3

所以要支持草案阶段的语法只要先安装对应的preset,

1
npm install babel-preset-stage-2

然后更改babel配置文件即可:

1234
{    "presets": ["es2015", "react", "stage-2"],    "plugins": []}

babel-polyfill

babel-polyfill 会模拟整个es6环境,例如在没有polyfill的情况下,以下代码:

123
function () {    return Array.from(arguments).map((a) => a + 2);}

会转换成

12345
function () {    return Array.from(argument).map(function (a) {        return a + 2;    });}

这段代码其实在很多浏览器(低版本的qq浏览器,百度浏览器等)下并不能正常工作,由于它们的js内核并不支持Array.from api:

1
Uncaught TypeError: Array.from is not a function

为了解决这个问题,我们需要添加一个polyfill, 一个polyfill本身就是一个代码片段,它实现了当前js运行环境未实现的本地api,babel采用corejs作为它的polyfill,采用 regenerator支持generators和async函数;

要支持babel polyfill功能,首先需要安装它:

1
npm install babel-polyfill --save-dev

然后在任何需要用到polyfill的文件的顶部引用该文件:

1
import 'babel-polyfill';

babel高级配置

很多人只是用babel 内置些 presets去完成一些工作,但其实babel的能力远不仅如此:

手工配置插件

babel的presets本身就是一系列预置的插件,如果你想添加一些特殊的支持,你可以手工添加额外的插件,例如你想让你的代码支持es7 的decorators,你只要先安装对应的decorators插件:

1
npm install babel-plugin-transform-decorators --save-dev

然后添加到.babelrc文件中即可:

1234
{  "presets": ["es2015"],  "plugins": ["transform-decorators"]}

你可以在babel官网查看babel 官方插件列表,你也可以在npm仓库查看开源社区贡献的babel插件列表

有些插件还可以额外添加一些配置项,例如很多插件会包含一个 “loose” 配置项用来指定 丢弃一些标准规范的行为,以便生成更简单,更健壮的代码;

12345
{   ...   plugins:  ["transform-es2015-classes", { "loose": true }]   ...}

分环境配置babel

babel有很多插件提供了对开发过程中的支持,同时也有很多插件提供了对生产环境的代码优化,你可以通过指定不同环境动态加载不同的babel插件:

1234567891011
{    "presets": ["es2015"],    "env": {        "development": {            "plugins": [...]        },        "production": {            "plugins": [...]        }    }}

当前的上下文环境是根据 process.env.BABEL_ENV 获取的,若没有,则尝试从 process.env.NODE_ENV 获取,若NODE_ENV也没有,则默认是 development 环境;

以下是分别在Unix和Windows系统上设置环境变量的方式:

Unix:

12
$ BABEL_ENV=development$ NODE_ENV=development

Windows:

12
$ SET BABEL_ENV=development$ SET NODE_ENV=development

当然更好的方式是使用类似cross-env的npm 包,它可以让你通过脚本参数指定环境变量。

构建自己的babel配置

每次写相同的babel配置文件其实很浪费时间,所以我们需要构建自己的presets模块

假设有如下的 .babelrc

1234
{  "presets": ["es2015", "react"],  "plugins": ["transform-decorators"]}

接下来你要做的就是命名该项目 babel-preset-* ,然后创建两个文件:
一个 package.json 文件:

12345678910
{  "name": "babel-preset-awesome",  "version": "1.0.0",  "author": "Kliment Petrov <[email protected]> (http://kleopetrov.me)",  "dependencies": {    "babel-preset-es2015": "^6.3.13",    "babel-preset-react": "^6.3.13",    "babel-plugin-transform-decorators": "^6.6.5",  }}

然后,创建一个 index.js 文件并导出 .babelrc 的上下文,将文件中的preset和插件改为用require的方式调用:

1234567891011
module.exports {    {        presets: [            require("es2015"),            require("react")        ],        plugins: [            require("transform-decorators")        ]    }}

最后将它发布到npm仓库即可;

其它工具

babel也可以和其它工具例如 linting,代码风格 配合一起使用

Linting

最有名的Linting工具非eslint莫属,babel将其整合到官方支持,首先,我们需要安装对应的包:

1
npm install eslint babel-eslint --save-dev

接下来,在你的项目下创建 .eslintrc 文件,并做配置:

123456
{    "parser": "babel-eslint",    "rules": {    ...    }}

最后在你的package.json配置lint脚本,然后执行npm run lint即可:

1234567
{    ...    "scripts": {        "lint": "eslint ./src/*.js*"    }    ...}

编辑器插件

由于babel使用者越来越多,各大ide也提供了相应的babel插件支持

总结

babel和其周边的生态在当今web开发中扮演越来越重要的角色,通过这篇文章的介绍,你可以通过配置尽情的使用最新的js规范及周边技术(JSX, Flow, 等等),话不多说,赶快开始吧!

原文:大专栏  关于babel,你应该知道的一些事

原文地址:https://www.cnblogs.com/wangziqiang123/p/11618430.html

时间: 2024-08-01 09:56:28

关于babel,你应该知道的一些事的相关文章

ReactJs和React Native的那些事

介绍 1,React Js的目的 是为了使前端的V层更具组件化,能更好的复用,它能够使用简单的html标签创建更多的自定义组件标签,内部绑定事件,同时可以让你从操作dom中解脱出来,只需要操作数据就会改变相应的dom. 2,React Native的目的 是希望我们能够使用前端的技术栈就可以创建出能够在不同平台运行的一个框架.可以创建出在移动端运行的app,但是性能可能比原声app差一点. 3,ReactJs和React Native的原理是相同的,都是由js实现的虚拟dom来驱动界面view层

babel入门

从前,一提到新东西,我的反应就是兼容性好不好,如果不能满足产品经理的需求,就还是用保守的方式实现吧.毕竟前端开发是一件很灵活的事,怎么写都行,至于为何会用某种方法,一定是综合考虑兼容性,性能,用户体验,开发成本等因素后再说.兼容性和新事物有时就像鱼和熊掌不可兼得,必须权衡利弊,做一个决断.但是ECMAScript 2015不一定要等所有浏览器都支持后才可以用,于是你会想到一个工具babel,它可以助ECMAScript 2015一臂之力,让处于某个stage的且尚未纳入es规范的特性提前支持,因

react.js 你应知道的9件事

React.js 初学者应该知道的 9 件事 本文假定你已经有了一下基本的概念.如果你不熟悉 component.props 或者 state 这些名词,你最好先去阅读下官方起步和手册.下面的代码示例我将使用 JSX 作演示,因为使用 JSX 语法写组件更为简洁,也更具表达力. 1. React.js 只是一个视图库 我们从最基本的开始.React 不是一个 MVC 框架,好吧,它根本就不是一个框架.它只是一个渲染视图的库.如果你对 MVC 熟悉的话,你就会意识到 React.js 只对应了V 

Babel(抽象语法树,又称AST)

文章:https://juejin.im/post/5a9315e46fb9a0633a711f25 https://github.com/jamiebuilds/babel-handbook/blob/master/translations/zh-Hans/plugin-handbook.md 你了解过Babel吗? 了解过抽象语法树,又称AST,有学习过,也写过一个基于AST的乞丐版模板引擎,先是词法解析token,然后生产抽象语法树,然后更改抽象语法树,当然这是插件做的事情,最后根据新的A

How Javascript works (Javascript工作原理) (十五) 类和继承及 Babel 和 TypeScript 代码转换探秘

个人总结:读完这篇文章需要15分钟,文章主要讲解了Babel和TypeScript的工作原理,(例如对es6 类的转换,是将原始es6代码转换为es5代码,这些代码中包含着类似于 _classCallCheck 和 _createClass这样的函数,而这些函数已经在Babel和TypeScript的标准库中预先定义好了,然后进行处理). 顺便温习了Object.create这个方法,  比如有一个obj:{name:'是ho',f:function(){alert(1)}} var a = O

深入浅出的webpack构建工具---babel之配置文件.babelrc(三)

阅读目录 一:理解 babel之配置文件.babelrc 基本配置项 二:在webpack中配置babel 回到顶部 一:理解 babel之配置文件.babelrc 基本配置项 1. 什么是babel? 它是干什么用的? ES6是2015年发布的下一代javascript语言标准,它引入了新的语法和API,使我们编写js代码更加得心应手,比如class,let,for...of promise等等这样的,但是可惜的是这些js新特性只被最新版本的浏览器支持,但是低版本浏览器并不支持,那么低版本浏览

深入理解webpack(三) babel之配置文件

一:理解 babel之配置文件.babelrc 基本配置项 1. 什么是babel? 它是干什么用的? ES6是2015年发布的下一代javascript语言标准,它引入了新的语法和API,使我们编写js代码更加得心应手,比如class,let,for...of promise等等这样的,但是可惜的是这些js新特性只被最新版本的浏览器支持,但是低版本浏览器并不支持,那么低版本浏览器下就需要一个转换工具,把es6代码转换成浏览器能识别的代码,babel就是这样的一个工具.可以理解为 babel是j

JavaScript是如何工作的:深入类和继承内部原理 + Babel和TypeScript之间转换

现在构建任何类型的软件项目最流行的方法这是使用类.在这篇文章中,探讨用 JavaScript 实现类的不同方法,以及如何构建类的结构.首先从深入研究原型工作原理,并分析在流行库中模拟基于类的继承的方法. 接下来是讲如何将新的语法转制为浏览器识别的语法,以及在 Babel 和 TypeScript 中使用它来引入ECMAScript 2015类的支持.最后,将以一些在 V8 中如何本机实现类的示例来结束本文. 概述 在 JavaScript 中,没有基本类型,创建的所有东西都是对象.例如,创建一个

@babel/preset-env 与@babel/plugin-transform-runtime 使用及场景区别

之前在用babel 的时候有个地方一直挺晕的,`@babel/preset-env` 和 `@babel/plugin-transform-runtime`都具有转换语法的能力, 并且都能实现按需 `polyfill` ,但是网上又找不到比较明确的答案, 趁这次尝试 roullp 的时候试了试. 如果我们什么都不做, 没有为babel 编写参数及配置, 那babel 并没有那么大的威力, 它什么都不会做, 正是因为各个预设插件的灵活组合.赋能, 让 babel 充满魅力, 创造奇迹 首先是 @b