一、前置知识
没接触过前端模块化概念的同学可先参考:JS & Node 模块化解释:AMD、UMD、CommonJS、 ESM
二、什么是 Rollup ?
Rollup
工具可以将代码转成不同模块,实现一套代码多端(浏览器/Node)引入。比如通过一句命令将代码打包为:
- 浏览器(代码通过 Script 标签引入)
rollup main.js --file bundle.js --format iife
- AMD(兼容 requirejs.js 框架)
rollup main.js --file bundle.js --format amd
- CommonJS(Node.js 代码通过 CJS 方式引入)
rollup main.js --file bundle.js --format cjs
- UMD (浏览器、AMD、CJS 均支持,是目前最常见的模块选择方式)
rollup main.js --file bundle.js --format umd --name "myBundle"
后面会提到每个命令的作用,这里了解即可。
三、Rollup 的应用场景和好处
-
如果你的项目是以插件或库给用户引入使用,Rollup 是最佳选择,它可以将代码转成不同的模块,然后用户根据自身项目模块语法来引入你的代码。
-
Rollup 支持 Tree-shaking ,只打包引用代码,无引用的一律甩掉。
-
你的项目可以肆无忌惮地使用 ESM 写法,Rollup 将会自动编译,再结合 Babel 美滋滋。
四、Rollup 与 Webpack/Vite 的区别
-
Rollup
将 JS 代码转成不同的引入模块形式,如果要处理其它语言需要借助插件。 -
Webpack
将 JS 代码进行打包压缩,同时拥有着 CSS/JS/HTML/Font 等其它语言插件的生态丰富圈。 -
组件库或插件
适合用 Rollup 打包、大型项目
适合用 Webpack 或 Vite 。
五、Rollup 与 Babel 的区别
-
Rollup
可将 JS 代码变成多种模块来引入运行。 -
Babel
可将高级 JS 语法代码转成低级版本兼容运行。
六、Rollup 使用教程
6.1 准备工作
-
新建项目:
rollup-example
-
项目结构:
-
src/main.js
代码:const user = () => { return { name: 'Jack' } } export { user };
-
全局安装 Rollup:
npm install rollup -g
6.2 使用命令行
6.2.1 使用 CLI 打包
rollup ./src/main.js --file lib.js --format cjs
解释:
-
./src/main.js
是目标即入口文件。 -
--file lib.js
是输出的产物文件名。 -
--format cjs
是需要转换的模块格式,这里我们采用CJS
,表示只用于 Node.js
打包后的产物:
6.2.2 参数命令说明
-o
=== --file
=== output
输出产物的文件名。-d
=== --dir
=== 输出产物的目录名,一般在开启 code spliting 代码分割技术后才用到。-f
=== --format
=== 打包模块格式。-w
=== --watch
=== 启动监听模式,当项目代码有变动时,自动执行打包命令。-c
=== --config
=== rollup.config.js
指向配置文件。
其它参数命令可参考官方文档。
6.3 使用配置文件
当频繁使用打包命令且参数量越来越多时,Rollup 支持配置文件的方式,例如:
// rollup.config.js
import json from '@rollup/plugin-json';
import terser from '@rollup/plugin-terser';
import resolve from '@rollup/plugin-node-resolve';
import babel from '@rollup/plugin-babel';
export default {
input: 'src/main.js', // 目标入口
// 同一个目标入口可以编译多种产物形式。
output: [
{
file: 'bundle.js', // 产物文件名。
format: 'cjs', // 产物模块格式。
},
{
file: 'bundle.min.js',
format: 'iife',
// output-plugin(构建完成后的插件):
// 做一些收尾工作,比如 terser 插件可将代码变量/函数名全部压缩转义为 a,b,c,d 的精简版本形式,俗称“混淆”,防止外部人员窥探源码。
plugins: [terser()]
}
],
// compliling-plulgin(rollup 执行编译时的插件):
// 帮助我们在写代码的过程中享受一些特殊语法糖和特殊处理。
plugins: [
// 支持识别 import json 数据。
json(),
// 支持 Babel (记得要在 babel.config.js 中配置下 preset )
resolve(),
babel({ babelHelpers: 'bundled' })
],
// 告诉哪个 NPM 模块打包过程种直接全量 import,不采用 tree-shaking 。
external: ['lodash']
};
最后执行 rollup -c
即可,更多配置选项可参考官方文档 。
提示:命令行参数的优先级比配置选项更高。
七、Rollup 支持打包 Vue 模板 或 Vue TSX
构建一个组件库时,通常需要借助框架来快速完成,比如我想构建一套 Vue 语法的组件库,能够给其它 Vue 项目引入使用。接下来我将以 Vue3 的两种写法来作为演示。
7.1 准备工作
-
新建
rollup-vue-example
项目并使用npm init -y
初始化。 -
项目结构如下:
-
为了使项目全面支持 ESM 模块语法,在
package.json
中新增:"type": "module"
,以便本地运行项目时 node 不会报错。 -
main.js
入口代码如下:import Vue from 'vue'; import App from './src/App.vue'; new Vue({ render: (h) => h(App), }).$mount('#app');
-
src/App.vue
代码如下<template> <div>Hello,world</div> </template> <script lang="ts"> import { defineComponent } from 'vue'; export default defineComponent({ setup(props) { return {} } }) </script> <style lang="scss" scoped> </style>
-
rollup.config.js
配置文件如下:export default { input: 'main.js', output: { file: 'dist/index.js', format: 'esm', }, plugins: [], };
7.2 打包 Vue 模板
要想让 Rollup
识别 .vue
文件,得分几个步骤完成:
7.2.1 安装以下两个插件:
npm i rollup-plugin-vue @vue/compiler-sfc
其中 rollup-plugin-vue
是我们想要的插件,@vue/compiler-sfc
是 rollup-plugin-vue 需要的依赖(后面会讲它的用处)。
7.2.2 调整 rollup.config.js
配置:
import vue from 'rollup-plugin-vue';
export default {
input: 'main.js',
output: {
file: 'dist/index.js',
format: 'esm',
},
plugins: [
vue({
css: true, // 提取 css 为单个文件。
compileTemplate: true, // 编译 vue 模板。
})
],
};
7.2.3 执行:
rollup -c
编译后的 dist/index.js
产物如下:
你可能会问,为什么 .vue 源码会被编译,而不像 js 代码那样原封不动的输出?
这是因为 .vue
语法本身就不能直接在浏览器或 node 上面跑,于是刚刚的 @vue/compiler-sfc
依赖就排上用场了,它可以识别 .vue
文件并编译成可执行的 JS 对象代码。
不信可以在产物里找找看哪个不是 JS 能识别的,若能找到;我请你喝可口可乐。
你可能还会问,那为啥本地项目就能跑起 vue 模板的代码呢?这是因为编译期间,如 vue-cli or vite 偷偷将它们转为可执行的 JS 脚本,只是我们没感知到而已~
7.3 打包 Vue JSX
Vue3 除了语法上发生了变化,它还支持 JSX 写法,我们又不得不继续卷到底!
与 Vue 模板相比,Rollup 支持 Vue JSX 需要多点配置量,但问题不大。
7.3.1 准备工作
我们继续沿用刚刚的 rollup-vue-example
项目来作为演示,这里稍微改动下即可:
- 新增
src/App.tsx
文件,内容如下:
import { defineComponent } from 'vue';
const App = defineComponent({
setup() {
const Greet = () => <div>Hello,world</div>
return <Greet />
}
});
export default App
- 改变
main.
引入文件方式:
import Vue from 'vue';
import App from './src/App.tsx'; // 引入 tsx 。
new Vue({
render: (h) => h(App),
}).$mount('#app');
7.3.2 安装依赖包:
npm i @rollup/plugin-babel @babel/core @vue/babel-preset-jsx
解释:
-
@rollup/plugin-babel
能够让 Rollup 支持Babel
。 -
@babel/core
引入babel
的核心编译包。 -
@vue/babel-preset-jsx
Vue 自家实现的Vue JSX
babel 插件 。
对 Babel
概念不熟的可以阅读前面写过的 JS & 介绍 Babel 的使用及 presets & plugins 的概念
。
7.3.2 调整 rollup.config.js
配置:
import vue from 'rollup-plugin-vue';
// 新增
import { babel } from '@rollup/plugin-babel';
export default {
input: 'main.js',
output: {
file: 'dist/index.js',
format: 'esm',
},
plugins: [
vue({
css: true, // 提取 css 为单个文件。
compileTemplate: true, // 编译 vue 目标。
}),
// 新增
babel({
extensions: ['.js', '.jsx', '.ts', '.tsx'],
presets: ['@vue/babel-preset-jsx'], // 让 babel 加载 Vue JSX babel 插件。
})
],
};
7.3.3 执行:
roolup -c
编译后的 dist/index.js
产物如下:
你可能会问,.tsx
采用的就是 JS 语法呀,产物为什么也会发生变化呢?
错!!!TSX 不是 JS,它们是 JS + HTML 的混合体,看看里面的标签便知,浏览器是无法执行这段代码的,依然需要转成可执行的JS 对象。
八、Rollup 常用插件集合
========compiling plugin=========
@rollup/plugin-commonjs 支持在 ESM 中引入 CJS
代码。
@rollup/plugin-typescript 支持识别 .ts
文件。
@rollup/plugin-json 能够导入 import .json
文件。
@rollup/plugin-babel 支持 Babel
@rollup/plugin-node-resolve 提供更全面的路径解析
========output plugin=========
@rollup/plugin-terser 将代码变量混淆,转成 a,b,c,d, …的形式。
查看更多插件
----------------------------------------------------------------结尾----------------------------------------------------------------文章来源:https://www.toymoban.com/news/detail-571700.html
参考文献:
https://rollup-plugin-vue.vuejs.org/#what-does-rollup-plugin-vue-do
https://rollupjs.org/introduction/
https://rollupjs.org/tutorial/
https://adostes.medium.com/authoring-a-javascript-library-that-works-everywhere-using-rollup-f1b4b527b2a9文章来源地址https://www.toymoban.com/news/detail-571700.html
到了这里,关于Rollup & 的作用、使用教程、支持 Vue、以及与 Webpack / Babel 的区别的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!