Rollup 是一个 JavaScript 的打包工具,目前我们常使用的 Webpack 也常拿来跟他做比较,基本上两者皆能达到我们想要的效果,但其各自有较擅长的领域,Webpack 适合应用程序的打包,而 Rollup 则比较适合 library 的打包,另外他使用上也比 Webpack 简单一些,接着就看一下怎麽使用吧!
首先我们开一个新专案,使用指令建立 package.json
$ npm init -y
然後我们简单的写一些东西
// index.js
const myFunction = async () => {
console.log('myFunction')
}
myFunction()
export default myFunction
运行後可以看到结果,如下:
$ node index.js
myFunction
Rollup 是一个针对 ES6 Module
所设计的打包工具,所以我们必须使用 ES6 Module
来做撰写,而使用方法有以下两种,选一种即可开始使用罗
ES Module
档案的副档名改为 .mjs
package.json
内加入 { "type": "module" }
首先安装今天的主角 Rollup
$ npm install --global rollup
接着可以执行指令进行打包
$ rollup index.js --file dist/bundle.js --format umd --name "myBundle"
-f, --format
:档案输出格式(amd, cjs, es, iife, umd, system)-n, --name
:档案全域名称-m, --sourcemap
:产生 sourcemap
-w, --watch
:监听档案变化即时编译-c, --config
:使用 rollup.config.js
的设定当需要的设定变多之後,我们可以创建 rollup.config.js
来详细写入相关的设定,以下有几个常用设定,详细的可以看官方文件
// rollup.config.js
const config = {
input: 'index.js', // 进入点
plugins: [], // 插件
external: [], // 外部插件
onwarn(warning, warn) { // 自定义警告
// do something...
},
treeshake: true, // 删除没用到的程序码
output: { // 输出档案
name: 'bundle', // 全域名称
file: 'dist/bundle.js', // 输出档案
format: umd, // 输出格式
sourcemap: true // 是否产生 sourcemap
}
}
export default config
最後我们可以在 package.json
加入指令,方便之後编译
// package.json
{
"scripts": {
"build": "rollup -c"
}
}
打包成果如下:
(function (global, factory) {
typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
typeof define === 'function' && define.amd ? define(factory) :
(global = typeof globalThis !== 'undefined' ? globalThis : global || self, global.bundle = factory());
}(this, (function () { 'use strict';
const myFunction = async () => {
console.log('myFunction');
};
myFunction();
return myFunction;
})));
通常打包时我们通常还会用到许多其他的功能,而插件就是来补齐这些功能,首先我们先修改一下程序码,安装一个 Demo 用的插件,并小小修改一下程序码
$ npm install the-answer
接着程序码如下:
// index.js
import answer from 'the-answer'
const action = () => {
return new Promise((res, rej) => {
setTimeout(() => {
res(answer)
}, 3000)
})
}
const myFunction = async () => {
const answer = await action()
console.log(answer)
}
myFunction()
export default myFunction
打包後会发现有一些错误,这些错误会靠着插件来解决,所以我们先看看有哪些常见的插件可以使用
resolve 协助我们从 node_modules
中找到我们安装的插件
$ npm install @rollup/plugin-node-resolve --save-dev
// rollup.config.js
import { nodeResolve } from '@rollup/plugin-node-resolve'
const config = {
input: 'index.js',
output: {
name: 'bundle',
file: 'dist/bundle.js',
format: 'umd'
},
plugins: [
nodeResolve()
// 如果要在浏览器使用需要加入设定如下
// nodeResolve({ browser: true, preferBuiltins: true })
]
}
export default config
commonjs 将 CommonJS
转换为 ES6 Module
$ npm install @rollup/plugin-commonjs --save-dev
// rollup.config.js
import commonjs from '@rollup/plugin-commonjs'
const config = {
input: 'index.js',
output: {
name: 'bundle',
file: 'dist/bundle.js',
format: 'umd'
},
plugins: [
commonjs()
// Node.js 有些套件需要加入以下设定才会正常
// commonjs({ include: ['node_modules/**'] })
]
}
export default config
json 将 .json
档案转换为 ES6 Module
$ npm install @rollup/plugin-json --save-dev
// rollup.config.js
import json from '@rollup/plugin-json'
const config = {
input: 'index.js',
output: {
name: 'bundle',
file: 'dist/bundle.js',
format: 'umd'
},
plugins: [
json()
]
}
export default config
builtins 与 globals 将一些 Node.js
内的全域变数变成 ES6 Module
$ npm install rollup-plugin-node-builtins --save-dev
$ npm install rollup-plugin-node-globals --save-dev
// rollup.config.js
import builtins from 'rollup-plugin-node-builtins'
import globals from 'rollup-plugin-node-globals'
const config = {
input: 'index.js',
output: {
name: 'bundle',
file: 'dist/bundle.js',
format: 'umd'
},
plugins: [
globals(),
builtins()
]
}
export default config
babel 将 ES6 的语法编译为浏览器看得懂的版本,另外还要下载它的核心
$ npm install @rollup/plugin-babel --save-dev
$ npm install @babel/core --save-dev
// rollup.config.js
import { babel } from '@rollup/plugin-babel'
const config = {
input: 'index.js',
output: {
name: 'bundle',
file: 'dist/bundle.js',
format: 'umd'
},
plugins: [
babel({ babelHelpers: 'bundled' })
]
}
export default config
接着要编写 babel 的设定档,我们在根目录建立一个 babel.config.js
,并安装 babel 的预设设定
$ npm install @babel/preset-env --save-dev
// babel.config.js
const config = {
presets: [
[
'@babel/preset-env'
]
]
}
export default config
最後在进入点加入 runtime.js
使其正常编译
// index.js
import 'regenerator-runtime/runtime.js'
terser 用来将程序码压缩
$ npm install rollup-plugin-terser --save-dev
// rollup.config.js
import { terser } from 'rollup-plugin-terser'
const config = {
input: 'index.js',
output: {
name: 'bundle',
file: 'dist/bundle.js',
format: 'umd'
},
plugins: [
terser()
]
}
export default config
以上差不多就是常用的插件,那麽我们来把刚刚编译的问题解决吧!
// rollup.config.js
import { nodeResolve } from '@rollup/plugin-node-resolve'
import commonjs from '@rollup/plugin-commonjs'
import { babel } from '@rollup/plugin-babel'
import { terser } from 'rollup-plugin-terser'
const config = {
input: 'index.js',
output: {
name: 'bundle',
file: 'dist/bundle.js',
format: 'umd'
},
plugins: [
nodeResolve({ browser: true, preferBuiltins: true }),
commonjs(),
babel({ babelHelpers: 'bundled' }),
terser()
]
}
export default config
// rollup.config.js
import { nodeResolve } from '@rollup/plugin-node-resolve'
import builtins from 'rollup-plugin-node-builtins'
import globals from 'rollup-plugin-node-globals'
import commonjs from '@rollup/plugin-commonjs'
import json from '@rollup/plugin-json'
import { babel } from '@rollup/plugin-babel'
import { terser } from 'rollup-plugin-terser'
const config = {
input: 'index.js',
output: {
name: 'bundle',
file: 'dist/bundle.js',
format: 'umd'
},
plugins: [
nodeResolve(),
globals(),
builtins(),
commonjs({ include: ['node_modules/**'] }),
json(),
babel({ babelHelpers: 'bundled' }),
terser()
]
}
export default config
到这边就可以正常打包罗!
顺便补充一下,如果想要把插件当成外部插件引用可以照以下设定,以浏览器举例
// rollup.config.js
import { nodeResolve } from '@rollup/plugin-node-resolve'
import commonjs from '@rollup/plugin-commonjs'
import { babel } from '@rollup/plugin-babel'
const config = {
input: 'index.js',
output: {
name: 'bundle',
file: 'dist/bundle.js',
format: 'umd',
globals: {
'the-answer': 'the-answer' // 全域变数
}
},
plugins: [
nodeResolve({ browser: true, preferBuiltins: true }),
commonjs(),
babel({ babelHelpers: 'bundled' })
],
external: ['the-answer'] // 告知为外部插件
}
export default config
最後另外提醒一下以下几点
Node.js
与浏览器环境有差异,要分开调整ES6 Module
撰写的话打包路径有可能会出现错误我只是想打包个 JavaScript 阿,搞这一大堆的搞了好几天,真的很苦啊呜呜,希望不要有人再掉进这个大坑
<<: Guaranteed Results with Updated SASM PDF Questions
>>: 进击的软件工程师之路-软件战斗营 第二十周(结训周)
三天前,我们已成功把静态档案加入 Angular 的专案了,如果感到有点陌生,可以再到以下连结,重新...
1.前言 今天依旧接续之前没讲完程序码,这次主要是讲loop里面的程序码,那此次主要介绍较为主要的部...
在经过一个月的学习之後,操作上只是理解有非常多可以客制化的部分,难免会想资讯图像化的部分到底可以炫技...
今天进度 : 鸟哥私房菜 - 第十五章、例行性工作排程(crontab) 使用 systemctl ...
前言 今天想跟大家讨论这个在团队内外之间都可能面对的「信任」问题。信任这件事,几乎大家都能理解它的重...