在Web开发领域,保持技术的更新是非常重要的。随着前端构建工具的快速发展,Webpack已经更新到5.x版本,如果你正在使用Vue2项目,并且还在使用Webpack 3,那么是时候考虑升级一下Webpack了。我最近将我的Vue2项目从Webpack 3升级到了Webpack 4。以下是我升级过程中积累的经验和步骤,希望能帮助那些准备进行类似升级的开发者。
写在前面
为什么不直接升级到webpack5.x?
这个问题问得很好,我最开始也是直接一键升级到最新版,一启动,直接报各种版本不匹配(哭),由于项目比较大引入的依赖太多,实在是难以推进,所以退而求其次,先升级到webpack4.x,后面再想办法往上升!!!
升级前的准备
在进行任何重大的项目改动之前,备份总是第一位的。请首先确保你的项目已经被推送到Git仓库,这样即使升级失败,也能轻松回退到之前的版本。
升级开始
我原本的webpack版本是^3.6.0,本次升级为:^4.46.0
我本次升级涉及到的文件目录如下:
1、更新package.json中Webpack和相关依赖
以下是我本次升级新增以及更新的依赖版本:
依赖 | 原版本 | 升级后版本 | 类型 |
babel-polyfill | -- | ^6.26.0 | 新增 |
babel-plugin-transform-es2015-modules-commonjs | -- | ^6.26.2 | 新增 |
html-webpack-plugin | ^2.30.1 | ^4.3.0 | 升级 |
mini-css-extract-plugin | -- | 0.9.0 | 新增 |
vue-loader | ^13.3.0 | ^15.7.0 | 升级 |
webpack | ^3.6.0 | ^4.46.0 | 升级 |
webpack-cli | -- | 3.3.12 | 新增 |
webpack-dev-server | ^2.11.5 | ^3.11.1 | 升级 |
2、安装依赖
npm install
如果由于项目中其他依赖冲突产生的报错及安装失败,可以加上--legacy-peer-deps
npm install --legacy-peer-deps
3、 逐步修改Webpack配置
.babelrc文件:
// 修改前
{
"presets": [
["env", {
"modules": false,
"targets": {
"browsers": ["> 1%", "last 2 versions", "not ie <= 8"]
}
}],
"stage-2"
],
"plugins": ["transform-vue-jsx", "transform-runtime"]
}
// 修改后
{
"presets": [
["env", {
"modules": false,
"targets": {
"browsers": ["> 1%", "last 2 versions", "not ie <= 8"]
}
}],
"stage-2"
],
"plugins": ["transform-vue-jsx", "transform-runtime","transform-es2015-modules-commonjs"]
}
build/utils.js文件:
// 删除或注释以下代码
const ExtractTextPlugin = require('extract-text-webpack-plugin')
// 改为
const MiniCssExtractPlugin = require('mini-css-extract-plugin')
// 删除或注释以下代码
if (options.extract) {
return ExtractTextPlugin.extract({
use: loaders,
fallback: 'vue-style-loader',
// https://www.cnblogs.com/luosiding/p/8268837.html
publicPath: '../../'
})
} else {
return ['vue-style-loader'].concat(loaders)
}
// 改为
return [options.extract ? MiniCssExtractPlugin.loader : 'vue-style-loader'].concat(loaders)
build/webpack.base.conf.js文件:
// 删除或注释以下代码
const vueLoaderConfig = require('./vue-loader.conf')
// 改为
const { VueLoaderPlugin } = require('vue-loader')
// module.exports中:
entry: {
app: './src/main.js'
},
// 改为:
entry: {
app: ['babel-polyfill', './src/main.js']
},
// 新增:
mode:process.env.NODE_ENV,
plugins: [
new VueLoaderPlugin()
],
// 删掉options
module: {
rules: [
//...(config.dev.useEslint ? [createLintingRule()] : []),
{
test: /\.vue$/,
loader: 'vue-loader',
options: vueLoaderConfig //删除该条
},
build/webpack.dev.conf.js文件:
如果项目中使用了jquery才改:
plugins: [
...,
new webpack.ProvidePlugin({
$: 'jquery'
})
]
build/webpack.prod.conf.js文件:
// 删掉或注释以下代码
const ExtractTextPlugin = require('extract-text-webpack-plugin')
// 改为
const MiniCssExtractPlugin = require('mini-css-extract-plugin')
// 删掉或注释以下代码
new UglifyJsPlugin({
uglifyOptions: {
compress: {
warnings: false
}
},
sourceMap: config.build.productionSourceMap,
parallel: true
}),
new ExtractTextPlugin({
filename: utils.assetsPath('css/[name].[contenthash].css'),
// Setting the following option to `false` will not extract CSS from codesplit chunks.
// Their CSS will instead be inserted dynamically with style-loader when the codesplit chunk has been loaded by webpack.
// It's currently set to `true` because we are seeing that sourcemaps are included in the codesplit bundle as well when it's `false`,
// increasing file size: https://github.com/vuejs-templates/webpack/issues/1110
allChunks: true,
}),
// 改为:
new MiniCssExtractPlugin({
filename: utils.assetsPath('css/[name].[contenthash].css'),
ignoreOrder: true
}),
// 删掉或注释以下代码:
chunksSortMode: 'dependency'
// 改为:
chunksSortMode: 'none'
// 删掉或注释以下代码:
new webpack.optimize.CommonsChunkPlugin({
name: 'vendor',
minChunks (module) {
// any required modules inside node_modules are extracted to vendor
return (
module.resource &&
/\.js$/.test(module.resource) &&
module.resource.indexOf(
path.join(__dirname, '../node_modules')
) === 0
)
}
}),
// extract webpack runtime and module manifest to its own file in order to
// prevent vendor hash from being updated whenever app bundle is updated
new webpack.optimize.CommonsChunkPlugin({
name: 'manifest',
minChunks: Infinity
}),
// This instance extracts shared chunks from code splitted chunks and bundles them
// in a separate chunk, similar to the vendor chunk
// see: https://webpack.js.org/plugins/commons-chunk-plugin/#extra-async-commons-chunk
new webpack.optimize.CommonsChunkPlugin({
name: 'app',
async: 'vendor-async',
children: true,
minChunks: 3
}),
// 改为:
optimization: {
minimizer: [
new UglifyJsPlugin({
parallel: true, // 开启多进程压缩。
uglifyOptions: {
output: { comments: false },
compress: {
warnings: false,
drop_debugger: true, // 是否清除debugger
drop_console: true // 是否清除所有console
// pure_funcs: ['console.log','console.info','console.warn','console.debug']
//drop_console 设置false,需要特殊清除的
}
},
sourceMap: config.build.productionSourceMap
})
],
splitChunks: {
chunks: 'async',
minSize: 30000, // 大于30KB才单独分离成chunk
maxAsyncRequests: 5,
maxInitialRequests: 3,
name: true,
cacheGroups: {
default: {
priority: -20,
reuseExistingChunk: true
},
// 生成 vendors.js,
vendors: {
name: 'vendors',
test: /[\\/]node_modules[\\/]/,
priority: 10,
chunks: 'all'
// enforce: true
},
common: {
name: 'common',
chunks: 'all',
minChunks: 2,
minSize: 0,
maxInitialRequests: 5 // The default limit is too small to showcase the effect
}
}
},
// 生成 manifest.js
runtimeChunk: {
name: 'manifest'
}
}
总结
如果改完可以正常启动,那么恭喜你!升级成功了!!如果不幸失败了,那么。。。很抱歉没有给你提供有效的帮助(哭),你也可以留言或私信,我看看有没有遇到类似报错。希望我的经验能帮助你在升级Vue2项目到Webpack 4的过程中少走弯路!
标签:extract,webpack,js,升级,Webpack,实操,Vue2,loader,true From: https://blog.csdn.net/Jiaberrr/article/details/142586400