0%

rollup使用总结

前言

项目中一直用的都是 webpack,前一段需要开发几个类库, 看过很多开源库源码都是用 rollup。这次通过开发类库,于是就快速上手了 rollup。

定位

Rollup 是一个 JavaScript 模块打包器,可以将小块代码编译成大块复杂的代码,例如 library 或应用程序。

与 Webpack 偏向于应用打包的定位不同,rollup.js 更专注于 Javascript 类库打包。

我们熟知的 Vue2、React 等诸多知名框架或类库都是通过 rollup.js 进行打包的。

常用配置

入口文件

Rollup 既然是打包类库文件,那么它的入口也就只能是 JS 文件了(通过第三方插件可以支持 Html,这里不作展开),因此我们新建一个 main.js 作为入口文件,打包出来的文件我们命名为 bundle.js,我们可以简单的通过命令行进行打包:

1
2
3
4
5
# 针对浏览器环境打包
rollup main.js --file bundle.js --format iife

# 针对Nodejs环境打包
rollup main.js --file bundle.js --format cjs

推荐使用配置文件进行打包:

1
2
3
4
5
# 默认使用rollup.config.js配置文件
rollup --config

# 使用自定义my.config.js配置文件
$ rollup --config my.config.js

一个基础的配置文件如下

1
2
3
4
5
6
7
8
// rollup.config.js
export default {
input: "main.js",
output: {
file: "bundle.js",
format: "cjs"
}
};

这里的 format 字段有六种选项:

  • amd: 异步模块定义,用于像 RequireJS 这样的模块加载器
  • cjs:CommonJS,适用于 Node 和 Browserify/Webpack
  • es:ES 模块文件
  • iife:自执行模块,适用于浏览器环境 script 标签
  • umd:通用模块定义,以 amd,cjs 和 iife 为一体
  • system:SystemJS 加载器格式

Rollup 也支持配置多个文件入口,我们新建 foo.js 和 bar.js 两个入口文件:

1
2
3
4
5
6
7
8
9
10
export default {
input: {
foo: './foo.js',
bar: './bar.js',
},
output: {
dir: 'dist',
format: 'cjs',
},
}

这样打包出来的两个文件就放入 dist 中。


插件(plugins)

  • @rollup/plugin-json
    • 可以读取 json 文件
  • @rollup/plugin-commonjs
    • 第三方的模块为了能够直接使用,往往不是 ES6 模块而是用 commonjs 的模块方式编写的,将 commonjs 的模块转化为 ES6 模块
  • @rollup/plugin-node-resolve
    • 帮助 rollup 查找 node_modules 里的三方模块
  • @rollup-plugin-alias
    • 提供 modules 名称的 alias 和 reslove 功能
  • @rollup/plugin-babel
    • 打包的时候使用 babel 编译 js 代码
  • @rollup/plugin-replace
    • 类似 Webpack 的 DefinePlugin, 可在源码中通过 process.env.NODE_ENV 用于构建区分环境.
  • rollup-plugin-typescript2
    • 这是对原始 rollup-plugin-typescript 的重写,这个版本比原始版本慢一些,但是它将打印出打字稿的句法和语义诊断消息(毕竟使用打字稿的主要原因)。使用该插件还有一个重要的原因,该插件能生成 声明文件 首先需要提供基础安装环境, 除了 typescript 基础环境 该插件需要依赖 tslib 去编译 ts 代码
  • rollup-plugin-terser
    • 可以打包压缩 es6 的 js 代码

外链(external)

我们在自己的库中需要使用第三方库,例如 vue 等,又不想在最终生成的打包文件中出现 vue,这个时候我们就需要 external 属性。

  1. 外部依赖的名称
  2. 一个已被找到路径的 ID(像文件的绝对路径)
1
2
3
4
5
6
7
8
9
10
// rollup.config.js
import path from 'path';

export default {
...,
external: [
'some-externally-required-library',
path.resolve( './src/some-local-file-that-should-not-be-bundled.js' )
]
};

全局模块(globals)

Object 形式的 id: name 键值对,用于umd/iife包。例如在这样的情况下

1
import $ from 'jquery';

我们想告诉 Rollup jquery 模块的 id 等同于 $ 变量:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
// rollup.config.js
export default {
...,
format: 'iife',
name: 'MyBundle',
globals: {
jquery: '$'
}
};

/*
var MyBundle = (function ($) {
// 代码到这里
}(window.jQuery));
*/.

Tree Shaking

由于 Rollup 本身支持 ES6 模块化规范,因此不需要额外配置即可进行 Tree Shaking


代码分割

import()实现了按需加载, rollup 内部会进行代码拆分,注意 format 不能用 iife 模式,因为 iife 会把所有模块放在同一个函数中


更多可参考大选项列表

总结

以上就是在开发类库的过程中对 rollup 的简单总结,接下来会进一步剖析 rollup 打包流程和原理。