Fork me on GitHub

gzip压缩初探

前言

我们平时工作中传文件时为了提高传输速度一般都会把文件压缩一下再传,那样速度回快一些,尤其是那些文件很多的文件夹,比较常用的压缩格式就是zip,rar了。那我们日常网页中利用http协议请求的那些资源可不可以压缩呢,当然是可以了,这就要说到我们今天的主角gzip了。

gzip之前我并没有在项目中用过,就每每查阅文档时听说某一个框架文件经gzip压缩之后就变得多小多小了,甚是好奇,所以今天特意查了一下。

gzip压缩的好处

好处当然是很明显的啦,就是可以大大减小传输文件的大小,提高页面加载速度、节省带宽。而且压缩的比率是可以调节的,我们常用的服务器端压缩是3到10倍,一个本来100k的文件能压缩到20k左右,想想都美滋滋,今天看了我们公司的官网用了gzip才发现压缩与不压缩差别还是蛮大的,哈哈。当然并不是所有的文件都能压缩这么多,像我们常用的CSS,JS文件是可以压缩很多的,而图片那些文件本来就压缩过了就没有多少可以压缩了。

gzip压缩的过程

gzip是一种流行的文件压缩算法,他会把文件压缩为.gz然后传给浏览器,最后浏览器负责解压文件呈现给客户。所以,要想实现文件的gzip压缩与解压,服务端和浏览器端都得支持。他们的通信过程大体如下:

  • 首先我们要将http请求的请求头中的==accept-encoding==属性设为gzip、deflate,表明浏览器支持gzip压缩方式
  • web服务器收到浏览器的请求之后,会判断浏览器是否支持gzip压缩,如果支持就传输压缩后的响应内容,如果不支持就传输未压缩的内容。当然,服务器会对压缩文件进行缓存,并不是每次请求都要再压缩一次
  • 浏览器接收到内容后判断文件是否被压缩,如果压缩了就先解压再解析(IE5.5以上才支持gzip)

谁来压缩

答案就两个,不是服务端就是客户端。

上面已经讲到了以前常用的一种方式是服务端压缩,浏览器解压。其实我们开发端可是可以压缩的,比如我们日常用的打包软件webpack就有compression-webpack-plugin这么个插件专门做压缩的,大概用法如下:

1
2
3
4
5
6
7
8
9
10
const CompressionWebpackPlugin = require('compression-webpack-plugin');

plugins: [
new CompressionPlugin({
test: /\.js/, //满足正则表达式的会被压缩
filename: '[path].gz[query]', //目标文件名
algorithm: 'gzip', //使用gzip压缩
threshold: 10240, //资源文件大于10240b=10k时会被压缩
})
]

既然已经存在了服务端响应请求时压缩,为什么还会存在应用构建时压缩这种方式呢?
存在并且被很多人使用就一定有它存在的价值,带着这份疑问我查询资料得知:gzip压缩文件是分等级的,共十级。等级越高压缩效果越好可也以为着更耗时嘛。如果你在服务端相应请求时压缩,那我请求一个文件不还是得等好久?而且即便是有了缓存,服务端压缩时还是有时间开销的。

但是构建时压缩就不存在上面这些问题了,我们现在的很多项目都是spa的项目,即使不是也是需要构建工具打包什么的,那我们在这个过程中就最大限度地使用gzip压缩代码,让服务器直接使用不是很好吗,反正我们也不会天天打包生产版本的,哈哈。

当然,这样服务端也得相应地更改配置来读取我们的压缩文件,会要麻烦一些,所以最终使用哪种压缩方式还得根据具有的哑无需求来,但是使用gzip压缩是很有必要的,毕竟效果是摆在那里的。

总结

在之前的一个vue单页面应用中我就遇到过打包之后文件还是太大的问题,当时经过各种分拆和异步组件之后首屏文件还是有一点大,我当时也想到了gzip,可当时的后台忽悠我说很麻烦,可我今天查了一下服务端压缩的话他们也不要加多少配置。所以啊,作为一个前端攻城狮服务端的知识多了解一下还是有必要的,可以防忽悠嘛,哈哈…

今天用uglifyjs-webpack-plugin这个插件配置代码压缩信息时才想起我们这个项目貌似木有使用gzip,于是乎从头了解了一下,所以记录一下。以后要多多利用起来!

参考