Rollup入门与进阶:为现代Web应用构建超小的打包文件

我们常常面临Webpack复杂配置或是Babel转译后的冗余代码,结果导致最终的包体积居高不下加载速度也变得异常缓慢,而在众多打包工具中Rollup作为一个轻量且高效的选择,正悄然改变着这一切,本文将带你深入了解这个令人惊艳的打包工具

目录

入门Rollup

配置Rollup

Babel转换代码

打包多入口代码

加载三方依赖模块

使用TS模块

压缩JS代码

模板生成html页面

启动开发服务器

处理vue组件

压缩CSS代码

设置环境变量

配置css预处理器

排除第三方库

打包文件拆分

生成sourcemap

配置路径别名

入门Rollup

        初识Rollup:是一个现代js的打包工具,主要用于将多个js文件打包成一个或多个最终的输出文件,它特别适用于构建库和模块化的应用程序,与Webpack等其他打包工具相比,Rollup 的一个显著优势是它能生成非常精简的代码,因为它能够进行更好的tree-shaking(去除未使用的代码)和模块优化,其使用特点如下所示:

1)打包后的代码体积小,性能优异

2)支持 ES 模块(ESM)格式

3)插件丰富,能够进行高度自定义

4)支持 tree shaking(去除无用代码)

所以说如果想构建库和小型应用,尤其是需要发布成npm包时,选择Rollup是一个不错的选择,如果想了解更为详细的内容,参考:官网 :

        项目初始化:接下来我们开始对项目进行一个初始化,首先终端执行如下命令直接全局安装rollup,如下所示:

npm install --global rollup

接下来我们创建一个项目文件夹,然后终端自行pnpm init初始化一个package.json文件,然后执行如下命令来安装一下rollup,安装完成之后,我们在项目根目录创建一个src文件夹,里面新建一个index.js文件,来展示一下要打包的代码:

pnpm i rollup -D
function random() {return Math.random().toString(16).slice(2);
}
console.log(random(), '变化1')
console.log(random(), '变化2')

然后我们根据官网给的入门提示,配置如下的打包命令:

可以看到打包出来的文件,基本上也是能够看懂的

配置Rollup

Rollup作为一个强大的js打包工具,在构建高效优化的模块化代码时展现了其独特的优势,然而Rollup的配置可以有很多细节,本文将带你逐步了解Rollup的配置过程,探讨如何通过Rollup配置优化打包提升代码的加载速度和运行效率,如下所示:

Babel转换代码

现代JavaScript特性(如箭头函数、模板字符串、类、模块化等)并不是所有浏览器都支持,特别是一些旧版浏览器(例如 Internet Explorer),Babel可以将这些新特性转换为旧版浏览器可以理解的代码以确保不同环境下的兼容性,接下来我们需要终端安装如下依赖:

// @babel/core babel的核心包
// @babel/preset-env 预设
// @rollup/plugin-babel babel插件
// @babel/runtime 减小最终构建文件的体积
// @babel/plugin-transform-runtime 减少转换过程中出现的重复代码
pnpm i @rollup/plugin-babel @babel/core @babel/preset-env @babel/runtime @babel/plugin-transform-runtime -D

安装完插件之后,我们在根目录创建一个 .babelrc 的babel配置文件,然后进行如下配置:

{"presets": [["@babel/preset-env",{"modules": false}]],"plugins": ["@babel/plugin-transform-runtime"]
}

配置完成之后我们来到config文件中进行如下babel插件的设置:

然后我们在入口文件写一个ES6模块的箭头函数,打包之后就会变成普通的function函数,兼容了低版本浏览器不支持ES6高级语法的情况:

打包多入口代码

上面我们配置的都是打包单入口的代码,如果想配置打包多入口的代码需要通过如下操作进行:

打包代码之前,我们需要先将打包文件中原本的文件先删除掉,这里需要借助如下插件:

pnpm i rollup-plugin-clear -D

然后我们引入插件之后进行如下插件的注册即可:

如下我们在dist文件下随便建一些文件,当我们执行打包之后,这些无关的文件都会被清除掉:

加载三方依赖模块

如果想rollup支持三方依赖插件的打包,这里我们需要安装如下插件然后进行一些配置:

pnpm i @rollup/plugin-node-resolve @rollup/plugin-commonjs -D

安装完成之后,我们仍然需要在配置文件当中进行如下插件的设置:

设置完成之后,我们可以安装一个三方依赖尝试一下,如下:

pnpm i lodash -s

如下当我们执行打包的时候就会把三方插件的依赖全部打包到文件当中:

当然可能还会有一些情况,比如说我们引入的第三方依赖当中含有的node语法,浏览器是无法识别的,这里我们需要替换一下打包结果中的关键字,终端执行如下命令:

pnpm i @rollup/plugin-replace -D

安装完成之后,在rollup配置文件当中进行如下配置即可:

replace({ // 替换打包结果中在浏览器中不兼容的代码,例如process.env.NODE_ENV'process.env.NODE_ENV': JSON.stringify('production'), // 替换代码中的环境变量preventAssignment: true // 防止替换赋值表达式,例如process.env.NODE_ENV = 'production'
}),

使用TS模块

如果想编译TS文件为js代码的话,需要终端安装如下插件:

pnpm i @rollup/plugin-typescript tslib -D

然后在配置文件中注册插件即可:

如下当执行打包的时候,TS文件编译成JS文件:

然后如果想对我们的ts编译进行一些操作的话,直接执行tsc --init生产ts配置文件,然后在里面调整即可,如下所示:

然后我们可以根据自身情况进行一个配置,例如如下所示:

{"compilerOptions": {"target": "ES6", // 编译目标为ES6                            "module": "ESNext", // 模块系统为ESNext                        "strict": false, // 启用所有严格类型检查选项                    "skipLibCheck": true, // 跳过所有声明文件的类型检查                    "esModuleInterop": true, // 允许从默认导出导入模块                    "forceConsistentCasingInFileNames": false, // 禁止对同一个文件的不一致的引用                    }
}

压缩JS代码

如果我们想对JS代码进行一个压缩,这里我们可以终端执行如下命令安装插件:

pnpm i @rollup/plugin-terser -D

安装完插件之后,还是对插件进行一个导入并使用:

然后我们执行打包,可以看到我们的代码已经真正被压缩了:

模板生成html页面

如果我们想根据模板html生成html单页面,这里我们可以终端执行如下命令安装插件:

pnpm i rollup-plugin-generate-html-template -D

安装完成之后,这里我们仍然需要在rollup配置文件当中,设置该模板插件,如下所示:

添加完成之后我们在src目录下新建一个index.html文件,这里可以演示作为vue的根节点:

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>Document</title>
</head>
<body><!-- vue的挂载点 --><div id="app"></div>
</body>
</html>

当我们执行打包命令之后,html页面就会自动被打包到dist文件下,并且会自动注入js代码,注入js代码的类型也是我们设置的module,当我们执行html之后,浏览器也会执行js中的代码逻辑:

启动开发服务器

上面我们通过模板生成index.htm文件之后,如果想方便的运行项目的话,这里我们可以安装如下插件来帮助我们快捷的实现服务器的运行:

pnpm i rollup-plugin-serve -D

安装完插件之后,我们就可以在rollup配置文件当中进行如下配置:

然后我们可以在package.json文件当中针对不同的环境执行不同的文件,这里本地环境就执行dev命令即可,生产环境就执行build命令即可,然后针对不同的环境也可执行不同的配置文件:

比如说生产的配置文件中,不需要执行启动开发服务器的插件,本地环境不需要执行压缩代码的插件,然后不同的环境替换关键字的命令也不同,如下所示:

然后我们运行pnpm run dev命令,打开本地环境,如下可以看到会自动打开浏览器,查看f12可以看到我们打包的命令被执行了:

如果想设置完开发服务器之后,后期对代码修改浏览器能够自动更新,可以终端执行如下命令:

pnpm i rollup-plugin-live-server -D

安装完插件之后,我们在配置文件中进行一个导入,然后我们修改页面代码之后,页面可以实时更新了,如下所示:

import { liveServer } from 'rollup-plugin-live-server'liveServer({port: 3000, // 设置端口号host: 'localhost', // 设置主机名root: 'dist', // 设置根目录file: 'index.html', // 设置默认打开的文件open: true, // 自动打开浏览器
})

当然我们还可以安装下面的插件,进行插件之间的配合操作,如下所示:

pnpm i rollup-plugin-livereload -D 
import serve from 'rollup-plugin-serve'
import livereload from 'rollup-plugin-livereload';// 开发服务器:使用 serve 和 livereload 组合
serve({open: true, // 只在首次启动时打开浏览器verbose: true,contentBase: ['dist'],port: 3000,host: 'localhost',onListening(server) {const address = server.address();const host = address.address === '::1' ? 'localhost' : address.address;const port = address.port;console.log(`Server running at http://${host}:${port}/`);}
}),
// 监听 dist 目录变化并自动刷新页面
livereload({watch: 'dist',verbose: false, // 关闭过多的日志输出delay: 1000, // 延迟时间,防止频繁刷新
}),

处理vue组件

如果我们想基于vue来开发一些功能的话,这里需要终端执行如下命令安装插件:

pnpm i vue -s
pnpm i rollup-plugin-vue -D

安装完插件之后,我们需要引入该插件,然后把vue编译放在插件列表的第一个:

然后我们开始编写vue模板并在入口文件中进行引入即可:

这里顺便为vue文件添加类型声明,如下所示:

终端执行打包命令之后,可以看到我们的浏览器已经打印了我们定义的内容:

压缩CSS代码

如果相对我们CSS代码进行一个压缩,这里我们可以终端执行如下命令安装插件,后面两个插件分别是对压缩和浏览器版本进行的控制:

pnpm i rollup-plugin-postcss cssnano autoprefixer -D

完整完插件之后,我们来到配置文件当中,进行如下配置:

import postcss from 'rollup-plugin-postcss';
import cssnano from 'cssnano';
import autoprefixer from 'autoprefixer'// 处理 CSS
postcss({extract: 'bundle.css', // 提取CSS到单独的文件modules: false, // 禁用 CSS Modulesminimize: true, // 开启压缩plugins: [autoprefixer, cssnano], // 使用 cssnano 插件进行压缩
}),

这里我们还需要来到package.json文件当中,设置browserslist指定项目所支持的浏览器范围的配置,如下所示:

"browserslist": ["defaults","not ie < 8","last 2 versions","> 1%","iOS 7","last 3 iOS versions"
]

执行打包命令之后,可以看到我们的css文件已经被压缩,并且浏览器的样式也成功生成,并且也兼容了其他浏览器的版本:

设置环境变量

如果想实现环境变量的配置以及实现跨平台等操作,可以安装如下插件:

pnpm i cross-env -D

然后我们在配置文件当中打印一下当前的环境变量,如下所示:

当我们在package包中配置好执行脚本命令之后,打包生产可以看到控制台打印了当前的环境变量为生产,与我们设置的是一样的:

然后我们根据打印的环境变量来控制台当前的rollup的一些配置,后期打包的话就会根据打包环境变量的不同来控制不同配置的生效: 

const isPro = process.env.NODE_ENV === 'production'// 处理 CSS
postcss({extract: 'bundle.css', // 提取CSS到单独的文件modules: false, // 禁用 CSS Modulesminimize: true, // 开启压缩plugins: [autoprefixer, // 使用 autoprefixer 插件添加浏览器前缀isPro && cssnano // 使用 cssnano 插件进行压缩], 
}),// 替换打包结果中在浏览器中不兼容的代码,例如process.env.NODE_ENV
replace({ 'process.env.NODE_ENV': JSON.stringify(process.env.NODE_ENV), // 替换代码中的环境变量preventAssignment: true // 防止替换赋值表达式,例如process.env.NODE_ENV = 'production'
}),// 压缩打包后的文件
isPro && terser(), // 生产环境才压缩代码

配置css预处理器

如果想使用一些css预处理器如scss的话,可以终端执行如下命令安装:

pnpm i sass -D
// 或
pnpm i less -D

安装完预处理器之后,我们可以直接使用这种css方式,如下所示:

然后浏览器的样式依然生效: 

排除第三方库

正常我们编写完vue项目之后打包项目,打包的文件里面就会把vue的项目全部打印到文件当中,可以看到打包后的文件为236kb,还是蛮大的,有什么办法能够减少打包体积呢?

这里我们可以排除第三方库的引入,通过第三方cdn方式引入来减少打包提交,如下我们可以在我们的index.html中引入vue对应版本的第三方cdn链接:

引入完之后我们可以在rollup的配置文件当中排除第三方vue的引入, 这里需要排除项配置和输出文件配置中的globals进行搭配使用,如下所示:

接下来当我们再次运行打包之后可以看到我们的打包体积已经大幅度被压缩了,有原本的200多kb的体积压缩到了只有1kb:

可以看到我们打包后的js文件是只有我们代码中真正写的内容,像vue的一些配置都被抽离出去通过cdn方式来引入使用了:

再比如当我们使用vue-router插件之后,配置完路由内容之后,如下所示:

虽然我们的项目被成功运行了,但是我们打包后的配置文件仍然还是比较大:

这里我们仍然可以通过排除第三方库的方式来减少打包体积,这里引入对应版本的vue-router文件

然后再配置文件当中,对路由依赖进行一个排除,如下所示:

可以看到我们的项目最终的打包体积被压缩到了3kb左右:

打包文件拆分

除了上面我们排除第三方库能够压缩打包体积操作,我们还可以对我们大体积的文件进行一个拆分操作,如果想对打包文件进行拆分,这里我们设置的打包模式就不能是iife,因为该模式不支持打包文件拆分,所有这里我们还是需要将其设置为esm模式,也就是es6里面所提供的浏览端标准的模块化解决方案,如下所示:

然后导入路由的方式我们采用异步方式导入,打包后的文件就会拆分成对应的路由文件,后面跟着一个随机的字符串避免浏览器缓存:

当然我们还可以对第三方库进行一个拆分,如下所示:

生成sourcemap

如果想我们压缩后的代码运行浏览器后,发生报错之后想精准定位报错文件,这里我们可以开启sourcemap操作,如下我们设置sourcemap为true的情况下,打包文件就会生成对应的map文件:

这些map文件就会被浏览器所识别并解析成我们项目真正的源代码,当然也可以设置如下选项,将这些map文件内嵌到对应的文件当中:

配置路径别名

如果想配置路径别名操作,可以终端执行如下命令安装插件:

pnpm i @rollup/plugin-alias -D

安装完插件之后,我们就需要在配置文件中进行一些设置,因为rollup配置文件中采用的是ES模块的写法,所有绝对路径我们需要改成ES写法:

import path from 'path'
import { fileURLToPath } from 'url';
import { dirname } from 'path';// 获取 __dirname 的 ES 模块写法
const __filename = fileURLToPath(import.meta.url);
const __dirname = dirname(__filename);

接下来我们在插件列表中进行如下配置:

// 配置别名路径
alias({entries: [{ find: '@', replacement: path.resolve(__dirname, 'src') }, // 将@替换为/src],
}),

然后路由代码中我们使用别名操作:

最终浏览器运行,没有问题,别名配置成功:

最后总结:Rollup作为一款专注于 ES 模块的打包工具,凭借其简洁的配置和强大的插件生态,为现代前端项目提供了高效、灵活的构建解决方案。通过本文的探讨,我们不仅掌握了从基础配置到高级优化的全流程技巧,还深入理解了如何根据项目需求选择合适的插件组合,解决实际开发中的各种挑战。无论是处理 Vue 组件、TypeScript 代码,还是实现热更新和代码分割,Rollup 都能以优雅的方式应对。掌握 Rollup 的配置艺术,不仅能提升项目的构建效率和运行性能,更能让开发者在模块化开发的道路上走得更加从容。未来,随着前端技术的不断演进,Rollup 也将持续为我们的开发工作注入新的活力,成为构建高质量JS应用不可或缺的利器。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/81325.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

基于C#的MQTT通信实战:从EMQX搭建到发布订阅全解析

MQTT(Message Queueing Telemetry Transport) 消息队列遥测传输&#xff0c;在物联网领域应用的很广泛&#xff0c;它是基于Publish/Subscribe模式&#xff0c;具有简单易用&#xff0c;支持QoS&#xff0c;传输效率高的特点。 它被设计用于低带宽&#xff0c;不稳定或高延迟的…

Mysql数据库之集群进阶

一、日志管理 5.7版本自定义路径时的文件需要自己提前创建好文件&#xff0c;不会自动创建&#xff0c;否则启动mysql会报错 错误日志 rpm包(yum) /var/log/mysql.log 默认错误日志 ###查询日志路径 [rootdb01 ~]# mysqladmin -uroot -pEgon123 variables | grep -w log_e…

当硅基存在成为人性延伸的注脚:论情感科技重构社会联结的可能性

在东京大学机器人实验室的档案室里&#xff0c;保存着一份泛黄的二战时期设计图——1943年日本陆军省秘密研发的“慰安妇替代品”草图。这个诞生于战争阴霾的金属躯体&#xff0c;与2025年上海进博会上展出的MetaBox AI伴侣形成时空对话&#xff1a;当人类将情感需求投射于硅基…

5月17日

这几天不知道为啥没更新。可能是玩得太疯了。或者是考试有点集中&#xff1f;&#xff1f; 线性代数开课了&#xff0c;英语昨天完成了debate 昨天中午debate结束我们就出去玩了&#xff0c;去的那里时光民俗&#xff0c;别墅很好&#xff0c;770平米&#xff0c;但是缺点是可…

FIFO的应用案例(基于Zephyr OS )

目录 概述 1. 软硬件环境 1.1 软件开发环境 1.2 硬件环境 2 FIFO的函数接口 3 FIFO的应用函数实现 3.1 实现步骤 3.2 代码设计 3.3 测试代码实现 3.4 源代码文件 4 编译和测试 4.1 编译代码 4.2 测试 概述 本文介绍了在nRF52832开发板上使用Zephyr操作系统进行…

AWS Elastic Beanstalk部署极简Spring工程(EB CLI失败版)

弃用 这里我没有走通EB CLI方式部署。 问题 最近又加入了AWS项目组&#xff0c;又要再次在AWS云上面部署Spring服务&#xff0c;我这里使用的使用AWS中国云。需要使用AWS Elastic Beanstalk部署一个极简Spring工程。 EB CLI安装 安装EB CLI之前需要先在本地安装好Git&…

粒子群算法(PSO算法)

粒子群算法概述 1.粒子群优化算法&#xff08;Particle Swarm Optimization&#xff0c;简称PSO&#xff09;。粒子群优化算法是在1995年由Kennedy博士和Eberhart博士一起提出的&#xff0c;它源于对鸟群捕食行为的研究。 2.基本核心是利用群体中的个体对信息的共享从而使得整…

leetcode2934. 最大化数组末位元素的最少操作次数-medium

1 题目&#xff1a;最大化数组末位元素的最少操作次数 官方标定难度&#xff1a;中 给你两个下标从 0 开始的整数数组 nums1 和 nums2 &#xff0c;这两个数组的长度都是 n 。 你可以执行一系列 操作&#xff08;可能不执行&#xff09;。 在每次操作中&#xff0c;你可以选…

Elasticsearch 官网阅读之 Term-level Queries

Term-level Queries 参考&#xff1a;https://www.elastic.co/docs/reference/query-languages/query-dsl/query-dsl-exists-query 一、Term Query Term Query 是 term 精准查询。需要注意的是&#xff0c;在进行 Term Query 的时候&#xff0c;要避免 text 类型的字段&#x…

信贷域——互联网金融业务

摘要 本文深入探讨了信贷域全托与半托业务的定义、特点、适用场景及注意事项&#xff0c;并分析了互联网金融核心信息流的多个方面&#xff0c;包括资金流、信息流、风险流、合规流、物流、技术流和商流&#xff0c;还阐述了金融系统“断直连”业务的相关内容&#xff0c;以及…

科技晚报 AI 速递:今日科技热点一览 丨 2025 年 5 月 17 日

科技晚报AI速递:今日科技热点一览 丨2025年5月17日 我们为您汇总今日的科技领域最新动向&#xff0c;带您快速了解前沿技术、突破性研究及行业趋势。 黄仁勋劝特朗普&#xff1a;AI 芯片出口规则得改&#xff0c;中国紧追其后&#xff1a;英伟达 CEO 黄仁勋在华盛顿 “山与谷论…

使用streamlit实现vLLM多实例信息统一监控

本文代码和配置文件实现了一个基于 Streamlit 和 FastAPI 的前后端分离的应用程序&#xff0c;用于管理和展示 VLLM&#xff08;Very Large Language Model&#xff09;实例的信息。以下是代码和配置文件的总结摘要&#xff1a; 概要 功能概述 前后端启动方式&#xff1a; 使用…

搭建一个WordPress网站需要多少成本

WordPress 最初可能只是一个简单的博客平台。但近年来&#xff0c;它不仅成为了最好的博客平台&#xff0c;还成为了一个全面的内容管理系统。白宫、jQuery、NGINX、《纽约时报》等企业都把 WordPress 作为自己的网上家园。 不过&#xff0c;它们只是其中的佼佼者。根据 Built…

飞帆控件 post or get it when it has get

我在这里分享两个链接&#xff1a; post_get_it 设计 - 飞帆 有人看出来这个控件是干什么用吗&#xff1f; 控件的配置&#xff1a;

AI智能体 | 使用Coze一键制作“假如书籍会说话”视频,18个作品狂吸17.6万粉,读书博主新标杆!(附保姆级教程)

目录 一、整体工作流设计 二、制作工作流 2.1 开始节点 2.2 大模型_生成对话文案 2.3 代码_字幕切割 2.4 画板_对话背景 2.5 循环_对话语音01 2.5.1 选择器_2 2.5.2 语音合成02 2.5.3 语音合成03 2.5.4 变量聚合_1 2.5.5 视频合成01 2.6 循环_3 2.6.1 选择器_3 …

mysql中4种扫描方式和聚簇索引非聚簇索引【爽文一篇】

目录 一 mysql的聚簇索引&非聚簇索引 1.1 数据表 1.2 聚簇索引 1.3 非聚簇索引 1.4 覆盖索引 二 mysql的4种扫描查询 2.1 全表扫描 2.2 索引扫描 2.3 覆盖索引扫描 2.4 回表扫描 2.5 总结 三 mysql的回表查询详解 3.1 回表查询 一 mysql的聚簇索引&非聚簇…

泛微对接金蝶云星空实战案例技术分享

前言 在企业信息化建设中&#xff0c;OA系统与ERP系统对接往往是一个复杂而关键的环节。OA系统通常具有高度的自定义性&#xff0c;其基础资料和单据可能与ERP系统存在字段不一致等问题。同时&#xff0c;OA系统涉及审批流程及流程发起方定义&#xff0c;增加了对接的复杂性。…

一种资源有限单片机处理cJSON数据的方法

一般单片机处理cJSON格式的数据都直接使用cJSON库&#xff0c;但对于Ram较小的单片机&#xff0c;由于资源有限&#xff0c;这并不合适&#xff0c;但我们可以根据cJSON数据的特定格式&#xff0c;使用土方法&#xff0c;直接对字符进行查找裁剪即可 //截取字符串str中字符a与…

关于软件测试开发的一些有趣的知识

文章目录 一、什么是测试&#xff1f;二、为什么要软件测试软件测试三、测试的岗位有哪些四 、软件测试和开发的区别五、走测试岗位为什么还要学开发。4、优秀的测试人员具备的素质我为什么走测试岗位 一、什么是测试&#xff1f; 其实这个问题说简单也不简单&#xff0c;说难…

【C++ 基础数论】质数判断

质数判断 质数&#xff1a;对于所有大于 1 的自然数而言&#xff0c;如果该数除 1 和自身以外没有其它因数 / 约数&#xff0c;则该数被称为为质数&#xff0c;质数也叫素数。 如何判定一个数是否为质数呢&#xff1f; 一个简单的方法是 试除法 &#xff1a; 对于一个数 n&…