如何使Webpack使用缓存后缀?

时间:2016-08-30 22:40:22

标签: javascript webpack browser-cache

在Webpack之前,我总是依赖于以下模式来进行"缓存破坏":

<script src="foo.js?cacheBust=12345" />

其中12345是在每次构建时为我生成的服务器的标记(它可能是Git哈希,但在我的情况下它不是。)

使用Webpack,我现在有两个文件:build.jschunk.1.js。由于我使用普通的脚本标记带来第一个,我可以使用上面的模式:

<script src="build.js?cacheBust=12345" />

但是,此时build.js会提取chunk.1.js,并且当它执行时,它不会包含缓存无效后缀。

我希望Webpack自动附加?cacheBust=12345,但我在构建时不知道12345部分,因此我无法将其包含在webpack.config ?cacheBust=12345中。 1}}。相反,我必须等到评估HTML页面,此时我从服务器获取令牌。

所以,我的问题是,有没有办法让Webpack查看用于获取初始文件的参数(例如。<form action="secondPage.php" method="post"> <select id="men" class="select_class1" name="subselector"> <option value="">Choose an Item</option> <option value="tsm">T-Shirt</option> <option value="lsm">Long Sleeve</option> <option value="tankm">Tank Top</option> </select> <input type="submit" value="submit" /> </form> )并在获取其他文件时附加相同的参数?

6 个答案:

答案 0 :(得分:36)

如果您希望以&#34; webpack方式实现缓存清除&#34;:

1。输出文件的哈希名称

将输出文件名更改为哈希生成的名称(在构建阶段)

output: {
    path: '/',
    filename: '[hash].js',
    chunkFilename: '[chunkhash].js',
},

从那时起,您的foo.jschunk.1.js将被称为e883ce503b831d4dde09.jsf900ab84da3ad9bd39cc.js。值得一提的是,这些文件的生成通常与生产和时间相关,更新cacheBust值。

2。如何包含未知文件名?

现在你的foo.js - 主文件以不知道的方式命名。要提取此文件名,您可以使用AssetsPlugin

const AssetsPlugin = require('assets-webpack-plugin');
const assetsPluginInstance = new AssetsPlugin();

并将此插件添加到webpack.config.js

plugins: [
    assetsPluginInstance
]

webpack-assets.json文件中,您应该看到类似

的内容
{
    "main": {
        "js": "/e883ce503b831d4dde09.js"
    }
}

您可以使用此文件指向主.js文件。有关详细信息,请参阅this answer

3。受益时间

我想如果您因修改chunk.2.js文件而进行应用制作,则可以从

更改文件路径
- build.js?cacheBust=12345
- chunk.1.js?cacheBust=12345
- chunk.2.js?cacheBust=12345
- chunk.2.js?cacheBust=12345

到新的

- build.js?cacheBust=12346   // modified referation to chunk.2.js file
- chunk.1.js?cacheBust=12346
- chunk.2.js?cacheBust=12346 // modified
- chunk.2.js?cacheBust=12346

如果您使用上述解决方案,您将获得免费缓存确定。现在filles将被称为

(以前的制作)

- e883ce503b831d4dde09.js
- f900ab84da3ad9bd39cc.js
- 5015cc82c7831915903f.js
- 8b6de52a46dd942a63a7.js

(新制作)

- c56322911935a8c9af13.js // modified referation to chunk.2.js file
- f900ab84da3ad9bd39cc.js
- cd2229826373edd7f3bc.js // modified
- 8b6de52a46dd942a63a7.js

现在 main filechunk.2.js名称已更改,您可以使用webpack方式免费获取此名称。

您可以在此处阅读有关长期缓存的更多信息https://medium.com/webpack/predictable-long-term-caching-with-webpack-d3eee1d3fa31

答案 1 :(得分:10)

您可以直接执行此操作

output: {
    filename: '[name].js?t=' + new Date().getTime(),
    chunkFilename: '[name]-chunk.js?t=' + new Date().getTime(),
    publicPath: './',
    path: path.resolve(__dirname, 'deploymentPackage')
}

答案 2 :(得分:2)

以下适用于 Webpack v5

webpack.config.js

module.exports = {
    // ...
    output: {
        filename: "[name].bundle.[chunkhash].js",
        path: path.resolve(__dirname, "dist"),
        assetModuleFilename: "images/[hash][ext][query]"
    },
    // ...
    optimization: {
        moduleIds: "deterministic",
    }
    // ...
}

使用散列很重要,例如 [chunkhash]

请注意,有不止一种方法可以做到这一点。

来源:https://webpack.js.org/guides/caching/

答案 3 :(得分:1)

您可以使用 HtmlWebpackPlugin

来自webpack.js.org/plugins/html-webpack-plugin的描述:

...插件可简化HTML文件的创建,以服务于您的Webpack捆绑包。这对于在文件名中包含哈希值(会更改每次编译) ...

的Webpack捆绑包尤其有用。

我的 webpack.config.js 的一部分:

// ...
const HtmlWebpackPlugin = require('html-webpack-plugin');
// ...
module.exports = {
   // ...
   plugins: [
      new HtmlWebpackPlugin({
         template: './assets/index.html',
         hash: true,
      }),
      // ...
   ]
};

如果hash: true,则将唯一的webpack编译哈希值附加到所有包含的脚本和CSS文件中。这对于清除缓存很有用。

有关github.com/jantimon/html-webpack-plugin上HtmlWebpackPlugin 选项的更多信息

由于这个选项,我得到了带有以下内容的输出html文件:

<!DOCTYPE html>
<html>
   <head>
      <!-- ... rest of my head code ... -->
      <link href="./css/styles.css?f42fdf96e2f7f678f9da" rel="stylesheet">
   </head>
   <body>
      <!-- ... rest of my body code ... -->
      <script type="text/javascript" src="./js/index.bundle.js?f42fdf96e2f7f678f9da"></script>
   </body>
</html>

我的项目的源代码:github.com/cichy380/html-starter-bs4-webpack

答案 4 :(得分:1)

还有很多方法来进行缓存清除,也可以使用webpack。我本人经常使用后缀技术,来到这篇文章中寻找答案。我使用的块与OP不同,因为我只引用了通过webpack运行的javascript中的块:

const componentPromise = import(/* webpackChunkName: "myDelayedSource" */ "path/to/myComponent/myComponent.js");

我发现用于缓存清除(在js内)的解决方案只是更改块的名称:

const componentPromise = import(/* webpackChunkName: "myDelayedSource_2020-05-14" */ "path/to/myComponent/myComponent.js");

这不会提供文件后缀,但是会更改文件名,引用该文件的脚本也将使用新文件名。

我希望这可以帮助某人。

答案 5 :(得分:1)

如果要在Webpack中使用name.js?cacheBust=1234格式的哈希,可以执行以下操作:

output: {
  filename: '[name].js',
  chunkFilename: '[name].js?cacheBust=[chunkhash]',
},

我正在使用Laraval Mix在Webpack中做非常相似的事情,在这个Github问题中找到了答案:https://github.com/JeffreyWay/laravel-mix/issues/2131