构建⼯具历史

2021-04-26  本文已影响0人  欢欣的膜笛

前端开发语⾔的诞⽣

前端主要的开发语⾔:HTML、CSS 和 JS 都诞⽣在 20 世纪 90 年代。2000 年前,⽹⻚呈现和交互都较为简单,开发框架和处理⼯具都在孕育中,即便是早期前端开发者所熟知的 jQuery 框架,也远未出现。

⽂件压缩与合并⼯具

2000 年以后的 10 年里,随着更多 CSS 与 JS 框架的诞生,代码优化的工具也应运而生。为了获得更好的访问体验,开发者需要更少的资源连接数与更小的文件体积,这就分别对应了两类工具:文件压缩工具和合并工具。

包管理工具

npm、yarn 等

任务式构建工具

Grunt vs Gulp
使⽤⾃动化的任务式构建⼯具来替代⼿⼯执⾏各种处理命令。

  1. 基本组成
    核⼼的处理⼯具(grunt-cli/gulpcli)、配置⽂件(Gruntfile/Gulpfile),以及⼀系列常⽤的任务插件(Clean、Watch、Copy、Concat、Uglify、CssMin、Spritesmith......)等。
    在项⽬⾥通过编写配置⽂件,就可以定义⼯作流程中的各种⾃动化构建处理,例如在发⽣变更时,通过 Watch 插件监控⽂件,从⽽⾃动执⾏代码的检查与压缩等。

  2. 差异性

    • 读写速度:Gulp 在处理任务的过程中基于 NodeJS 的数据流,本质上是操作读写内存,⽽ Grunt 则是基于临时⽂件,因此在读写速度上 Gulp 要快于 Grunt
    • 社区使⽤规模:下载量 Gulp 要远多于 Grunt,⽽在插件数量⽅⾯,Grunt 要多于 Gulp 。
    • 配置⽂件的易⽤性:相⽐描述不同插件配置信息的 Gruntfile ⽽⾔,使⽤ pipe 函数描述任务处理过程的⽅式通常更易于阅读,但编写时需要对数据流有更深⼊的理解。

模块化的不同规范

  1. CommonJS
    在 CommonJS 出现之前,⼀个 JS 类库只能通过暴露全局对象的⽅式,供
    其他 JS ⽂件使⽤,这样的⽅式有着诸多的问题,例如变量污染等。CommonJS 作为⾮浏览器端的 JS 规范,它的基本要素如下:

    • 模块定义:⼀个模块即是⼀个 JS ⽂件,代码中⾃带 module 指向当前模块对象;⾃带 exports=module.exports,且 exports 只能是对象,⽤于添加导出的属性和⽅法;⾃带 require ⽅法⽤于引⽤其他模块。
    • 模块引⽤:通过引⽤ require() 函数来实现模块的引⽤,参数可以是相对路径也可以是绝对路径。在绝对路径的情况下,会按照 node_modules 规则递归查找,在解析失败的情况下,会抛出异常。
    • 模块加载:require() 的执⾏过程是同步的。执⾏时即进⼊到被依赖模块的执⾏上下⽂中,执⾏完毕后再执⾏依赖模块的后续代码。
  2. AMD
    CommonJS 的 Modules/1.0 规范从⼀开始就注定了只能⽤于服务端,不能⽤于浏览器端。这⼀⽅⾯是因为模块⽂件中没有函数包裹,变量直接暴露到全局;另⼀⽅⾯则因为浏览器端的⽂件需要经过⽹络下载,不适合同步的依赖加载⽅式,因此出现了适⽤于浏览器端的模块化规范 AMD。AMD 规范的基本要素如下:

    • 模块定义:通过 define(id?, dependencies?, factory) 函数定义模块。id 为模块标识,dependencies 为依赖的模块,factory 为⼯⼚函数。factory 传⼊的参数与 dependencies 对应,若不传 dependencies,则 factory 需要默认传⼊ require、exports,以及 module,或只传⼊ require,但使⽤ return 做导出。
    • 模块引⽤:最早需要通过 require([id], callback) ⽅式引⽤,之后也⽀持了类似 CommonJS 的 var a = require('a') 的写法。
  3. UMD
    UMD 本质上是兼容 CommonJS 与 AMD 这两种规范的代码语法糖,通过判断执⾏上下⽂中是否包含 define 或 module 来包装模块代码,适⽤于需要跨前后端的模块。

  4. ES Module

    • 模块定义:模块内⽀持两种导出⽅式,⼀种通过 export 关键字导出任意个数的变量,另⼀种通过 export default 导出,⼀个模块中只能包含⼀个 default 的导出类型。
    • 模块引⽤:通过 import 关键字引⽤其他模块。引⽤⽅式分为静态引⽤和动态引⽤。静态引⽤格式为 import importClause from ModuleSpecifier,import 表达式需要写在⽂件最外层上下⽂中;动态引⽤的⽅式则是 import(),返回 promise 对象。

模块化的构建⼯具

  1. RequireJS:RequireJS 的核⼼功能是⽀持 AMD ⻛格的模块化代码运⾏。
  2. Browserify:Browserify 的⽬标是让 CommonJS ⻛格的代码也运⾏在浏览器端,除了提供语法糖外,还提供了⼀些经过处理后且在浏览器端运⾏的 NodeJS 的核⼼模块。
  3. Babel:Babel 的定位⼀直是 Transformer,即语法转换器,它承担着将 ES6、JSX 等语法转换为 ES5 语法的核⼼功能,被⼴泛地运⽤于其他构建⼯具中。
  4. SystemJS:SystemJS 是兼容各种模块化规范的运行时工具。
  5. Webpack:Webpack ⼀⽅⾯兼容各种模块化规范的标识⽅法,另⼀⽅⾯将模块化的概念延伸到其他类型的⽂件中,创造性地打造了⼀种完全基于模块的新的构建体系。
  6. Rollup:Rollup 在诞⽣之初率先实现了 Tree Shaking 功能,以及天然⽀持 ES6 模块的打包。
上一篇下一篇

猜你喜欢

热点阅读