问题说明,修改dllPlugin之后,加载网页报错,Cannot read property 'call' of undefined。
原因:
以util.dll.js为例说明。
原本编译后会把lodash和dayjs打包变为 util.dll.js(旧版util.dll.js)
// webpack.dll.config.js
module.exports = {
...,
entry: {
util: ['lodash', 'dayjs'],
...
}
}
修改entry中的util,新增了一个exceljs模块。
// webpack.dll.config.js
module.exports = {
...,
entry: {
util: ['lodash', 'dayjs', 'exceljs' ],
...
}
}
编译后会把lodash、dayjs以及exceljs打包变为 util.dll.js (新版util.dll.js)
项目编译后,使用exceljs的地方会指向util.dll.js。这个时候如果用户浏览器的缓存还在,使用exceljs的页面一旦加载,由于缓存的存在,文件指向了旧版的util.dll.js,旧版的util.dll.js中没有exceljs,就会报错。(Cannot read property 'call' of undefined)
解决这个问题的思想是把新版、旧版的util.dll.js在文件名上做出区分。
这样就有两个思路:
1、文件名加hash。
2、文件名加时间戳。
第1种,走不通。说下实现方案和问题所在。在output中加上[hash:8]
// webpack.dll.config.js
module.exports = {
...,
entry: {
util: ['lodash', 'dayjs'],
...
},
output: {
...
filename: '[name].[hash:8].dll.js'
}
}
webpack可以识别这种[hash:8]通配符,dll编译后成功加上了文件名成功加上了hash。
(如 /dll/util.2d0b32f5.1aefa32d.js)
但是在vue.config.js的导入dllplugin过程中,无法动态的将带hash值的dll文件名导入。因此这条路走不通。
第2种,加时间戳(加年月日)可行。
首先创建时间戳,可以通过原生js的Date对象,也可以通过第三方库,这里以dayjs为例。
// webpack.dll.config.js
const dayjs = require("dayjs");
const date = dayjs.format("YYYYMMDD");
module.exports = {
...,
entry: {
util: ['lodash', 'dayjs'],
...
},
output: {
...
filename: `[name].${date}.dll.js`
}
}
(编译后的dll文件名,形如 /dll/util.20220210.js)
在vue.config.js中也创建时间戳(年月日)
// vue.config.js
const dayjs = require("dayjs");
const date = dayjs.format("YYYYMMDD");
在fileArr中,将filePath配置项修改
(结合我写的https://segmentfault.com/a/11... 这篇文章看)
上图红框所指部分的模板字符串,改为dll/${dllName}.${date}.dll.js
完结