vue-cli项目包体积过大,完美解决教程
使用cdn打包时,把vue、vuex、vue-router、axios等,换用国内的bootcdn 直接引入到根目录的index.html中。在webpack设置中添加externals,忽略不需要打包的库。externals: { 'vue': 'Vue', 'vue-router': 'VueRouter', 'vuex': 'Vuex', 'axios': 'axios' } ...
前言:最新打包vue cli 项目时,体积尽然达到了12M,影响页面访问的速度,因此进行尝试优化,最终压缩到 668k ,效果明显。下面是优化方法。
一、BundleAnalyzer
作用:展示打包图形化信息,会打开一个html页面,帮助自己分析哪些文件过大,可针对其进行优化,上线前
注释掉
安装 webpack-bundle-analyzer
插件
npm install webpack-bundle-analyzer --save-dev
在 vue.config.js:
里面:
// 引入
const BundleAnalyzerPlugin = require("webpack-bundle-analyzer").BundleAnalyzerPlugin;
// 展示图形化信息
chainWebpack: config => {
config
.plugin('webpack-bundle-analyzer')
.use(BundleAnalyzerPlugin)
}
二、使用cdn
打包时,把vue、vuex、vue-router、axios等,换用国内的bootcdn 直接引入到根目录的index.html中。
在webpack设置中添加externals,忽略不需要打包的库。
externals: { 'vue': 'Vue', 'vue-router': 'VueRouter', 'vuex': 'Vuex', 'axios': 'axios' }
在index.html中使用cdn引入。
<script src="//cdn.bootcss.com/vue/2.5.2/vue.min.js"></script>
<script src="//cdn.bootcss.com/vue-router/3.0.1/vue-router.min.js"></script>
<script src="//cdn.bootcss.com/vuex/2.4.1/vuex.min.js"></script>
<script src="//cdn.bootcss.com/axios/0.15.3/axios.min.js"></script>
<script src="//cdn.bootcss.com/element-ui/2.5.4/index.js"></script>
三、组件异步加载(按需加载)
1、使用() => import() --es6提案
{
path: '/lock',
name: '锁屏页',
component: () =>
import( /* webpackChunkName: "page" */ '@/page/lock/index'),
meta: {
keepAlive: true,
isTab: false,
isAuth: false
}
},
{
path: '/404',
component: () =>
import( /* webpackChunkName: "page1" */ '@/components/error-page/404'),
name: '404',
meta: {
keepAlive: true,
isTab: false,
isAuth: false
}
},
根据webpackChunkName的不同,上面2个组件,将会被分成2个块打包,最终打包之后与组件相关的js文件会分为2个
2、 require.ensure 官方推荐
const Province = r => require.ensure([], () => r(require('@/components/Province.vue')), 'chunkname1')
const Segment = r => require.ensure([], () => r(require('@/components/Segment.vue')), 'chunkname1')
const Loading = r => require.ensure([], () => r(require('@/components/Loading.vue')), 'chunkname3')
const User = r => require.ensure([], () => r(require('@/components/User.vue')), 'chunkname3')
根据 chunkame的不同, 上面的四个组件, 将会被分成3个块打包,最终打包之后与组件相关的js文件会分为3个
四、压缩代码并移除console
安装 uglifyjs-webpack-plugin
在 vue.config.js文件引入
const UglifyJsPlugin = require('uglifyjs-webpack-plugin');
configureWebpack: {
optimization: {
minimizer: [
new UglifyJsPlugin({
uglifyOptions: {
compress: {
// warnings: false,
drop_console: true, //注释console
drop_debugger: false,
pure_funcs: ['console.log'] //移除console
}
}
})
]
}
},
五、gzip压缩代码
安装 compression-webpack-plugin
插件
npm install compression-webpack-plugin -D
在 vue.config.js
里面:
const CompressionWebpackPlugin = require('compression-webpack-plugin');
configureWebpack: {
plugins: (() => {
let plugins = []
if (isProduction) {
plugins.push(new UglifyJsPlugin({ // 代码压缩
uglifyOptions: {
//生产环境自动删除console
compress: {
// warnings: false, // 若打包错误,则注释这行
drop_debugger: true,
drop_console: true,
pure_funcs: ['console.log']
}
},
sourceMap: false,
parallel: true
}))
plugins.push(new CompressionWebpackPlugin({ // gzip压缩
algorithm: 'gzip',
test: new RegExp(
'\\.(' + ['html', 'js', 'json', 'css'].join('|') + ')$'
),
threshold: 10240, //对超过10k的数据压缩
minRatio: 0.8,
deleteOriginalAssets: false //不删除源文件
}))
}
plugins.push(new webpack.DefinePlugin({
"process.argv": JSON.stringify(process.argv)
}))
return plugins
})()
}
六、代码分割
在 vue.config.js
里面:
configureWebpack: {
optimization: {
runtimeChunk: 'single',
splitChunks: {
chunks: 'all',
maxInitialRequests: Infinity,
minSize: 1000 * 60,
cacheGroups: {
common: {
name: `chunk-common`,
minChunks: 2,
priority: 2,
chunks: 'initial',
reuseExistingChunk: true//如果当前块包含已经从主包中分离出来的模块,那么该模块将被重用,而不是生成新的模块
},
vendor: {
test: /[\\/]node_modules[\\/]/,
name(module) {
// 排除node_modules 然后吧 @ 替换为空 ,考虑到服务器的兼容
const packageName = module.context.match(/[\\/]node_modules[\\/](.*?)([\\/]|$)/)[1]
return `${name}.${packageName.replace('@', '')}`
}
}
}
}
},
}
SplitChunks插件配置选项
chunks 选项,决定要提取哪些模块
默认是 async :只提取异步加载的模块出来打包到一个文件中。
异步加载的模块:通过 import(‘xxx’) 或 require([‘xxx’],() =>{}) 加载的模块。
initial:提取同步加载和异步加载模块;
如果 xxx 在项目中异步加载了,也同步加载了,那么 xxx 这个模块会被提取两次,分别打包到不同的文件中。
同步加载的模块:通过 import xxx 或 require(‘xxx’) 加载的模块。
all:不管异步加载还是同步加载的模块都提取出来,打包到一个文件中;
minSize 选项:规定被提取的模块在压缩前的大小最小值,单位为字节;
默认为30000,只有超过了30000字节才会被提取。
maxSize 选项:把提取出来的模块打包生成的文件大小不能超过maxSize值;
如果超过了,要对其进行分割并打包生成新的文件。
单位为字节,默认为0,表示不限制大小。
minChunks 选项:表示要被提取的模块最小被引用次数,引用次数超过或等于minChunks值,才能被提取。
maxAsyncRequests 选项:最大的按需(异步)加载次数,默认为 6;
maxInitialRequests 选项:打包后的入口文件加载时,还能同时加载js文件的数量(包括入口文件),默认为4。
优先级 :maxInitialRequests / maxAsyncRequests < maxSize < minSize;
automaticNameDelimiter 选项:打包生成的js文件名的分割符,默认为:~
name选项:打包生成 js 文件的名称;
cacheGroups 选项,核心重点,配置提取模块的方案,里面每一项代表一个提取模块的方案。
下面是 cacheGroups 每项中特有的选项,其余选项和外面一致,若 cacheGroups 每项中有,就按配置的,没有就使用外面配置的;
test 选项:用来匹配要提取的模块的资源路径或名称,值是正则或函数;
priority 选项:方案的优先级,值越大表示提取模块时优先采用此方案,默认值为0;
reuseExistingChunk 选项:true / false。
为true时,如果当前要提取的模块,在已经在打包生成的js文件中存在,则将重用该模块,而不是把当前要提取的模块打包生成新的 js 文件。
enforce选项:true / false。
为true时,忽略minSize,minChunks,maxAsyncRequests和maxInitialRequests外面选项
配置选项很多,在实际项目中使用 SplitChunks,让你更深刻理解这些配置选项。
七、prefetch 和 preload
删除无用的插件,避免加载多余的资源(如果不删除的话,则会在 index.html 里面加载 无用的 js 文件)
chainWebpack: config => {
// 移除prefetch插件,避免加载多余的资源
config.plugins.delete('prefetch')
/ 移除 preload 插件,避免加载多余的资源
config.plugins.delete('preload');
}
八、抽离 css 支持按需加载
安装 mini-css-extract-plugin
插件
npm install mini-css-extract-plugin -D
在 vue.config.js
里面:
chainWebpack: config => {
let miniCssExtractPlugin = new MiniCssExtractPlugin({
filename: 'assets/[name].[hash:8].css',
chunkFilename: 'assets/[name].[hash:8].css'
})
config.plugin('extract-css').use(miniCssExtractPlugin)
}
九、图片按需加载
安装image-webpack-loader
插件
npm install image-webpack-loader -D
在 vue.config.js
里面:
config.module.rule('images')
.test(/\.(png|jpe?g|gif|webp)(\?.*)?$/)
.use('image-webpack-loader')
.loader('image-webpack-loader')
.options({
bypassOnDebug: true
})
.end()
更多推荐
所有评论(0)