「这是我参与2022首次更文挑战的第23天,活动详情查看:2022首次更文挑战」
前言
本文将一步一步构建一个使用 Rollup 打包的项目,并且介绍 Rollup 中插件的作用,最后带着大家实现最简单的通过不同的命令行打出不同的包的效果。
什么是 Rollup?
Rollup 是一个 JavaScript 模块打包器,可以将小块代码编译成大块复杂的代码
就像比较常听说的 Webpack 和 Esbuild。Rollup 也是为了将我们写的多个模块的代码按照我们的需求打包变成特定的格式,使其最后能够运行在浏览器环境上。
我们可以使用:
npm install --global rollup
来安装 Rollup 并且在进行一些基本的配置之后就可以成功的进行打包,具体的教程可以查看官方文档:
Rollup 的基本使用
- 首先我们需要新建一个测试项目,项目名叫做
my-rollup,使用:
npm init
初始化一下项目,并且安装上 rollup 依赖。
npm install rollup --global
这是全局安装 Rollup,由于我们后面还需要自定义安装,使用还需要 Rollup 中的 api,需要将 Rollup 安装到 node_module 中去。
npm install rollup
- 接着我们使用两个小文件来测试一下 Rollup 的打包功能
在目录下新建 src 文件夹
// src/main.js
import foo from './foo.js';
export default function () {
console.log(foo);
}
// src/foo.js
export default "hello world!";
- 接着使用 Rollup 进行打包,打包的方式有两种,一种是通过命令行传入打包参数
rollup src/main.js -o bundle.js -f cjs
文件目录下成功多出一个 bundle.js 文件,通过 node 测试打包结果:
PS D:\my-rollup> node
Welcome to Node.js v14.17.6.
Type ".help" for more information.
> var bundle = require('./bundle.js')
undefined
> bundle()
hello world!
打包成功。
- 除了命令行传入参数的方式,我们还可以通过配置文件来进行打包的配置,新建 rollup.config.js 文件,并且添加简单的打包参数。
// rollup.config.js
export default {
input: 'src/main.js',
output: {
file: 'bundle.js',
format: 'cjs'
}
};
- 这样就可以通过配置文件的配置来进行打包:
rollup -c
Rollup 的插件使用
在我们项目越来越大之后,我们的打包要求可能不在只是仅限于简单的js文件,可能会有各种各样的文件的加入,在这个时候,我们就需要使用到 Rollup 的插件
关于插件,在你如果使用了 Rollup 不认识的文件的情况下,Rollup 打包时会报错提醒,比方说我在项目中引入了json文件:
import { version, name } from "../package.json";
export default function () {
console.log("version " + version);
console.log("name " + name);
}
那么打包就会报错
他告诉我们需要使用 rollup-plugin-json 这个插件,那我们接下来就来安装一下这个插件,并且尝试着使用它。
- 安装插件依赖:
npm install --save-dev rollup-plugin-json
- 在 Rollup 配置文件中引入我们下载的插件
// rollup.config.js
import json from "rollup-plugin-json";
export default {
input: "src/main.js",
output: {
file: "bundle.js",
format: "cjs",
},
plugins: [json()],
};
- 打包,打包成功可以去查看打包文件 bundle.js
我们成功读取了 json 文件中的数据,并且只拿到了我们想要的,这就是 rollup-plugin-json 这个插件的作用,并不会拿到整个的 json 对象,而是会去拿需要的属性。
Rollup 中还有很多的插件,比如 打包css文件,ts文件,img文件,等等,我们可以根据项目的需求来安装对应的插件来实现打包。
通过 API 来实现自定义打包
API 的简单使用
Rollup 不只是可以通过 命令行接口(command line interface) 的方式配合可选配置文件来调用,还可以通过 JavaScript API 调用。
这就是为什么上面我们要在项目中安装 Rollup,Rollup 给我们暴露了一个对象
const rollup = require("rollup");
console.log("rollup", rollup);
可以看到,这个对象对外暴露了一些方法和属性,而我们要使用的,就是 rollup 这个方法,这是方法调用后会执行打包,并且可以传入一个对象,这个对象就是我们的配置对象。
接着我们配置一下我们的 "scripts" 方便我们后面进行调试,调用 bulid 的时候直接运行我们的 bulid.js 进行项目打包
"scripts": {
"build": "node scripts/build.js"
},
并且在项目下新建 scrpit 文件夹存放 build.js 打包模块并且方便后续加入其它配置
然后在 rollup 下的 rollup 方法就是调用打包的方法,并且它会返回一个 promise 对象,并且这个对象上面有一个 write 方法,rollup 传入的就是打包相关的输入配置:
const inputOptions = {
// 核心参数
input, // 唯一必填参数
external,
plugins,
// 高级参数
onwarn,
cache,
// 危险参数
acorn,
context,
moduleContext,
legacy
};
write 方法传入的就是输出所需要的配置对象:
const outputOptions = {
// 核心参数
file, // 若有bundle.write,必填
format, // 必填
name,
globals,
// 高级参数
paths,
banner,
footer,
intro,
outro,
sourcemap,
sourcemapFile,
interop,
// 危险区域
exports,
amd,
indent
strict
};
有了这两个方法,我们就可以简单的使用 API 来进行打包
const option = {
inputOptions: {
input: "src/main.js",
},
outputOptions: {
file: "./bundle.js",
format: "cjs",
},
};
const rollup = require("rollup");
console.log("rollup", rollup);
async function build() {
const outputOptions = option.outputOptions;
const inputOptions = option.inputOptions;
const bundle = await rollup.rollup(inputOptions);
await bundle.write(outputOptions);
}
build();
运行之后就可以和正常的命令行打包一样在目录下生成 bundle.js
使用 API 自定义打包选项
既然我们能够通过调用 "scripts" 命令的方式进行打包,那么是不是也可以把相关的配置选项加入 "scripts" 然后不同的参数会调用不同的打包选项呢,这里简单的实现一个打包输出不同文件名的例子。
- 配置我们的多个选项。既然要实现多个不同的配置选项,那么就需要多个不同的配置对象,来实现各种自定义。
const option1 = {
inputOptions: {
input: "src/main.js",
},
outputOptions: {
file: "./bundle1.js",
format: "cjs",
},
};
const option2 = {
inputOptions: {
input: "src/main.js",
},
outputOptions: {
file: "./bundle2.js",
format: "cjs",
},
};
- 接着我们实现第二条打包命令,并且传入我们决定好的标识:
"scripts": {
"build": "node scripts/bulid.js",
"build:two": "npm run build -- use-option2"
},
- 在 build.js 的打包函数中 通过 process.argv 拿到命令行输入,这样就可以判断执行的是哪一个打包命令:
if (process.argv[2] == "use option2") {
option = option2;
} else {
option = option1;
}
- 接着我们运行不同的命令,就能够在文件下生成不同的打包文件:
- 这样我们就算是实现了一个最简单的自定义命令进行不同的打包。
接着我们可以根据自己的需求,来配置更多的打包参数,这样就能够使得打包变得更加的灵活,根据需求的不同,打出不同的版本的包来。
总结
在很多的优秀项目当中,也是使用的类似的打包方法打出不同的需求的包来,比如我们最常见的 vue 项目也是类似的形式,接下去我们会再去说说在 vue 中,它是怎么根据配置的不同,来灵活的实现打包自定义的。