webpack 打包时遇到 chunk.js?v=xxxxxxx 的问题

· 约 7 分钟读完

在使用 webpack 进行前端打包时,经常会遇到缓存问题。其中一个常见问题就是在 js 文件名后面出现 ?v=xxxxxxx 的情况,例如 chunk.js?v=1234567。这种情况通常意味着浏览器无法识别文件是否已更改,从而无法正确获取最新的文件版本。因此,本文将介绍这种问题的根本原因,并提供几种可能的解决方法。

问题根源

在 webpack 打包时,为了减少文件下载时间和减小文件体积,它会将多个 JS 文件打包成一个或多个 bundle。这些 bundle 文件的名字是由 webpack 自动生成的哈希值,而这个哈希只随着文件内容的改变而改变。同时,webpack 又会生成一个名为 manifest.json 的文件,记录每个 bundle 的哈希值。因此,当打包后我们访问页面时,浏览器会下载这些 bundle 文件和 manifest.json 文件,然后根据 manifest.json 文件的内容去匹配对应的 bundle,从而正确加载我们的页面。

然而,有些情况下我们打包出来的文件名并不带哈希值,而是带有一个类似 ?v=xxxxxxx 的查询字符串。这个字符串实际上是被添加到文件路径后面的,而 webpack 默认并不会为文件添加这个字符串。所以,这个字符串的产生肯定是由某些别的操作引起的。

解决方法

方法一:手动指定 output.filename

最简单的解决方法是手动指定 webpack 的 output.filename 配置,将哈希值添加到文件名后面。例如:

这样做的好处是,我们可以很方便地自定义文件名,同时还可以避免截取文件名来解析哈希值的麻烦。

方法二:使用 HtmlWebpackPlugin 插件

Webpack 也有一个叫做 HtmlWebpackPlugin 的插件,它可以自动生成 index.html 文件,并自动在其中引用打包后的 JS 和 CSS 文件。使用这个插件时,我们可以通过设置其 hash 选项来在文件路径后添加哈希值,例如:

这样在打包后,生成的 index.html 文件中就会自动添加查询字符串,例如:

方法三:使用 AssetsPlugin 插件

另外一个可选的插件是 AssetsPlugin,它可以在打包结束后自动构建明文的资源清单,以便于维护打包后的文件。使用这个插件时,我们可以通过它的配置项来控制是否在文件名中添加哈希值,例如:

这样,在打包后生成的 assets-manifest.json 文件中,我们就可以很方便地查看每个文件的路径和文件名,例如:

方法四:手动编写一个插件

最后我们也可以编写一个自己的插件,来在打包时为文件名添加哈希值。这个插件代码较为复杂,但它也是最灵活的解决方案。其具体实现可参考以下示例代码:

在使用它时,我们只需要将它加入到 webpack 的插件数组中即可:

结语

在前端开发中,我们经常需要使用 webpack 进行打包。然而,由于浏览器缓存的存在,打包后的代码很容易出现缓存问题。本文介绍了一个常见的缓存问题 —— 在文件名后面添加查询字符串 ?v=xxxxxxx,并提供了几种可能的解决方法。希望能够帮助到有类似问题的读者。

来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/67d64abca941bf7134bfe923