背景
项目越做越大,页面越来越多,导致项目也越来越卡顿。
解决思路
- 1、首屏优化
- 2、技术债务编码优化
- 3、打包优化,cdn
首屏优化
在Vue项目中,引入到工程中的所有js、css文件,编译时都会被打包进vendor.js,浏览器在加载该文件之后才能开始显示首屏。若是引入的库众多,那么vendor.js文件体积将会相当的大,影响首屏的体验。利用webpack的externals配置。防止将某些 import 的包(package)打包到 bundle 中,而是在运行时(runtime)再去从外部获取这些扩展依赖(external dependencies)。
- 首先安装webpack的可视化资源分析工具,命令行执行:
'# NPM npm i webpack-bundle-analyzer -D # Yarn yarn add -D webpack-bundle-analyzer
2.1 然后在webpack的dev开发模式配置中,引入插件,代码如下:const { BundleAnalyzerPlugin } = require('webpack-bundle-analyzer')
plugins: [
new BundleAnalyzerPlugin()
]
2.2 vue-cli3中vue.config.js中加入配置
chainWebpack: (config) => {
// 关闭prefetch: vue-cli3 默认会把所有通过import()按需加载的javascript文件加上 prefetch
config.plugins.delete('prefetch');
// 打包分析插件
config.plugin('webpack-bundle-analyzer').use(require('webpack-bundle-analyzer').BundleAnalyzerPlugin);
// 复写html指令,防止xss攻击
config.module
.rule('vue')
.use('vue-loader')
.loader('vue-loader')
.tap((options) => {
options.compilerOptions.directives = {
html(node, directiveMeta) {
(node.props || (node.props = [])).push({
name: 'innerHTML',
value: `$xss.process(_s(${directiveMeta.value}))`,
});
},
};
return options;
});
}
-
最后命令行执行npm run build –report , 浏览器会自动打开分析结果
-
app.xxx.js 文件过大
解决方案:
- 代码分割 CommonsChunkPlugin;
- 提取第三方库 vendor
- 外部引入第三方库 external
- 设置缓存
- 代码压缩 uglifyJsPlugin
引入CommonChunkPlugin,并在router/index.js中使用require.ensure()进行组件的引入:
一、对于第三方js库的优化,分离打包
生产环境是内网的话,就把资源放内网,通过静态文件引入,会比node_modules和外网CDN的打包加载快很多。如果有外网的话,可以通过CDN方式引入,因为不用占用访问外网的带宽,不仅可以为您节省流量,还能通过CDN加速,获得更快的访问速度。但是要注意下,如果你引用的CDN 资源存在于第三方服务器,在安全性上并不完全可控。
目前采用引入依赖包生产环境的js文件方式加载,直接通过window可以访问暴露出的全局变量,不必通过import引入,Vue.use去注册
在webpack的dev开发配置文件中, 加入如下参数,可以分离打包第三方资源包,key为依赖包名称,value是源码抛出来的全局变量。如下图所示,可以看到打包后vue相关资源包已经排除在外了。对于一些其他的工具库,尽量采用按需引入的方式。
externals: {
vue: 'Vue',
vuex: 'Vuex',
'vue-router': 'VueRouter',
axios: 'axios',
'element-ui': 'ELEMENT'
}
四、开启gizp压缩
gizp压缩是一种http请求优化方式,通过减少文件体积来提高加载速度。html、js、css文件甚至json数据都可以用它压缩,可以减小60%以上的体积。前端配置gzip压缩,并且服务端使用nginx开启gzip,用来减小网络传输的流量大小。 命令行执行:npm i compression-webpack-plugin -D在webpack的dev开发配置文件中加入如下代码:const CompressionWebpackPlugin = require(‘compression-webpack-plugin’)
plugins: [
new CompressionWebpackPlugin()
]
前端项目配置Gzip的两种方式 1、静态压缩:前端工程打包成Gzip,然后nginx开启Gzip模块
- vue-cli生成的项目,安装 compression-webpack-plugin 插件
- nginx配置gizp
listen 4300; server_name localhost; location / { root /home/static/web/wechat; index /index.html; try_files $uri $uri/ /index.html; gzip_static on; #静态压缩 }
2、直接采用nginx进行Gzip化 2.1 nginx配置gizp ``` 在nginx.conf文件夹的http里面配置数据
gzip on; #开启或关闭gzip on off gzip_min_length 5k; #gzip压缩最小文件大小,超出进行压缩(自行调节) gzip_buffers 4 16k; #buffer 不用修改 gzip_comp_level 8; #压缩级别:1-10,数字越大压缩的越好,时间也越长 gzip_types text/plain application/x-javascript application/javascript text/css application/xml text/javascript application/x-httpd-php image/jpeg image/gif image/png; # 压缩文件类型 gzip_vary on; # 和http头有关系,加个vary头,给代理服务器用的,有的浏览器支持压缩,有的不支持,所以避免浪费不支持的也压缩,所以根据客户端的HTTP头来判断,是否需要压缩
2.2 开启gzip
gzip on;
启用gzip压缩的最小文件,小于设置值的文件将不会压缩
gzip_min_length 1k;
gzip 压缩级别,1-9,数字越大压缩的越好,也越占用CPU时间,后面会有详细说明
gzip_comp_level 1;
进行压缩的文件类型。javascript有多种形式。其中的值可以在 mime.types 文件中找到。
gzip_types text/plain application/javascript application/x-javascript text/css application/xml text/javascript application/x-httpd-php image/jpeg image/gif image/png application/vnd.ms-fontobject font/ttf font/opentype font/x-woff image/svg+xml;
是否在http header中添加Vary: Accept-Encoding,建议开启
gzip_vary on;
禁用IE 6 gzip
gzip_disable “MSIE [1-6].”;
设置压缩所需要的缓冲区大小
gzip_buffers 32 4k;
设置gzip压缩针对的HTTP协议版本
gzip_http_version 1.0; ```
前后端gzip压缩区别; nginx开启gzip 压缩会耗费cpu资源;会降低
双端Gzip区别及其意义 不同之处在于:
- 1、Webpack压缩会在构建运行期间一次压缩文件,然后将这些压缩版本保存到磁盘。
- 2、nginx在请求时压缩文件时,某些包可能内置了缓存,因此性能损失只发生一次(或不经常),但通常不同之处在于,这将在响应 HTTP请求时发生。
- 3、对于实时压缩,让上游代理(例如 Nginx)处理 gzip和缓存通常更高效,因为它们是专门为此而构建的,并且不会遭受服务端程序运行时的开销(许多都是用C语言编写的) 。
- 4、使用 Webpack的好处是, Nginx每次请求服务端都要压缩很久才回返回信息回来,不仅服务器开销会增大很多,请求方也会等的不耐烦。我们在 Webpack打包时就直接生成高压缩等级的文件,作为静态资源放在服务器上,这时将 Nginx作为二重保障就会高效很多。
- 5、注:具体是在请求时实时压缩,或在构建时去生成压缩文件,就要看项目业务情况。
原则: 1、小文件无需压缩,浪费资源 2、图片/mp3这样的二进制文件,不必压缩 因为压缩率比较小, 比如100->80字节