file-loader的踩坑
踩坑一:当我配置好file-loader之后运行npm run build,构建完成之后打开index.html,发现图片显示不出来,然后dist文件夹中还会多出一个显示不了的图片
html代码 .bg-image { background-image: url("../img/jx.png"); }
原因:
css-loader会默认帮你转换url -> url(image.png) => require('./image.png') 官网的解释 webpack 中文文档 (docschina.org)
然后会有对应的file-loader来帮你处理,但是webpack5里面又会默认帮你使用asset 模块进行处理,所以原因就是他们两个就冲突了
解决方案:
当在 webpack 5 中使用旧的 assets loader(如 file-loader/url-loader/raw-loader 等)和 asset 模块时,你可能想停止当前 asset 模块的处理,并再次启动处理,这可能会导致 asset 重复,你可以通过将 asset 模块的类型设置为 'javascript/auto' 来解决。 来自官方文档 webpack 中文文档 (docschina.org)
{ test: /\.(png|jpe?g|gif|svg)$/, use: [ { loader: 'file-loader', } ], type: 'javascript/auto' }
踩坑二:就算上面的配置完成之后,打包后的图片依旧显示不了,而且对资源的引用后面的路径变成了 /[object%20Module]
原因:
file-loader新版本默认使用了esModule语法,造成了引用图片文件时的方式和以前的版本不一样,而我们css-loader对url的处理又是将其转换成require()语句(commonjs语法)
解决:
1.
//在require后面加上.default const imgEl = new Image(); imgEl.src = require('../img/dsj.png').default
2.
{ test: /\.(png|jpe?g|gif|svg)$/, use: [ { loader: 'file-loader', options: { //不使用esModule的语法导出 esModule: false }, } ], type: 'javascript/auto' }
推荐使用第二种