Vue项目优化-代码压缩

网站应用的性能优化对于提高用户留存、转化率等都有积极影响。而减少传输大小是提高加载性能的一个常见方法。

本文介绍下Vue项目开启gzip压缩的方法。

Vue项目开启gzip压缩

安装compression-webpack-plugin

1
npm install --save-dev compression-webpack-plugin

这里有可能会碰到这个错误:

1
Cannot read property 'tapPromise' of undefined

这是因为compression-webpack-plugin这个版本高了,需要降低版本,因此,我们可以先卸载掉之前安装的版本,然后指定低版本安装。经过试验,6.1.1版本是可以正常运行的:

1
npm install --save-dev compression-webpack-plugin@6.1.1

vue.config.js配置configureWebpack

vue.config.js是vue-cli3之后新增的一个功能,再这个版本里面如果要配置webpack相关的属性,就需要自己在项目根目录新建vue.config.js这个文件,然后在该文件里面去写入你需要的配置等等。(配置vue-cli3项目,可以说是all in vue.config.js

当然,封装、就一定会留个口给用户,去对底层进行自定义操作。vue.config.js的配置项中,有两个口,configureWebpack和chainWebpack。

configureWebpack是调整webpack配置最简单的一种方式,可以新增也可以覆盖cli中的配置。

Type: Object | Function

  • 如果这个值是一个对象,则会通过 webpack-merge 合并到最终的配置中。

  • 如果这个值是一个函数,则会接收被解析的配置作为参数。该函数及可以修改配置并不返回任何东西,也可以返回一个被克隆或合并过的配置版本。

这个属性特别之处就是,他有两种类型形态,但是又不能重复使用,而在某些情况既需要对象类型的配置,也需要函数类型的配置

这里我使用函数类型的配置,这样可以基于环境有条件地配置行为,进行一些逻辑处理,直接修改或新增配置。

具体例子:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
// 引入compression-webpack-plugin
const CompressionPlugin = require('compression-webpack-plugin');

module.exports = {
configureWebpack:config =>{
// 仅在生产环境打包时对JS\CSS文件进行压缩
if(process.env.NODE_ENV === 'production'){
config.plugins.push(
new CompressionPlugin({
/* [file]被替换为原始资产文件名。
[path]替换为原始资产的路径。
[dir]替换为原始资产的目录。
[name]被替换为原始资产的文件名。
[ext]替换为原始资产的扩展名。
[query]被查询替换。*/
filename: '[path].gz[query]',
// 压缩算法
algorithm: 'gzip',
// 匹配文件
test: /\.js$|\.css$|\.html$/,
// 压缩超过此大小的文件,以字节为单位
threshold: 10240,
minRatio: 0.8,
// 是否删除原始文件只保留压缩后的文件
deleteOriginalAssets: false
})
)
}
}
}

配置了这个之后,打包可能会出现警告:

1
Conflict: Multiple assets emit different content to the same filename assets/js/.gz

这是因为打包之后命名都是空

问题在于filename: '[path].gz[query]'这个配置,这个版本下("compression-webpack-plugin": "^6.1.1")的配置应该修改为:filename: '[path][base].gz'

在打包后的静态文件中,可以看到有很多.gz的同名文件,这个就是gzip压缩后的文件,基本上可以压缩3-5倍左右。

nginx开启gzip

核心配置代码如下:

1
2
3
4
5
6
7
gzip on; #开启或关闭gzip on off
    gzip_disable "msie6"; #不使用gzip IE6
    gzip_min_length 100k; #gzip压缩最小文件大小,超出进行压缩(自行调节)
    gzip_buffers 4 16k; #buffer 不用修改
    gzip_comp_level 8; #压缩级别:1-10,数字越大压缩的越好,时间也越长
    gzip_types text/plain application/x-javascript text/css application/xml text/javascript application/x-httpd-php image/jpeg image/gif image/png; #  压缩文件类型
    gzip_static on; # nginx 会优先匹配你的 gzip 文件来返回,如果没有就寻找相应资源进行 gzip 压缩再返回

gzip on这个配置作用是,当nginx服务器返回gzip_types中列出的内容类型时,先使用gzip进行压缩(当然,前提是请求方支持gzip)。但是存在一个问题,返回内容是在请求服务器的时候使用gzip进行压缩的。对于同一个资源的不同请求,反复压缩,这无疑会增加服务器的CPU和内存消耗。

因此,一个更好的办法就是在Vue工程打包的时候就进行gzip压缩,也就是我们前面讲的通过compression-webpack-plugin插件配置在打包时进行gzip压缩,然后我们把gzip_static设置为on,这样在访问资源的时候,如果存在资源路径.gz的文件,则会直接返回该文件,其优先级高于动态的gzip。

查看是否已开启gzip压缩

Chrome浏览器F12打开控制台,进入Network调试界面,在表头单击鼠标右键,勾选Response Headers -> Content-Encoding后,在表头会多出Content-Encoding这一列,用于判断是否开启gzip(如已开启Gzip,Content-Encoding会显示gzip)。

我们把鼠标移到这些请求的Size上会显示:xxx transferred over network, resource size: xxx这里transferred over network是网络加载的资源大小,而resource size则是资源经过解压后的大小

参考


----------- 本文结束啦感谢您阅读 -----------

赞赏一杯咖啡

欢迎关注我的其它发布渠道