WP5 模块联合:remoteEntry.js 缓存

如何解决WP5 模块联合:remoteEntry.js 缓存

使用 Webpack 5 模块联合,如果远程入口被修改,你不需要重新部署主模块/应用程序,当浏览器请求时,将加载最新版本的模块。

我想知道:由于远程 URL 保持不变(例如 http://localhost:8081/remoteEntry.js),浏览器可能会在每次加载主模块时缓存文件和加载的缓存版本。另一方面,如果您为远程条目添加缓存破坏,您将没有缓存。

假设有一个使用 Webpack 5 Module federation 的具有微前端架构的应用程序。有一个远程微前端,配置如下:

output: {
  publicPath: "http://localhost:8081/",},plugins: [
  new ModuleFederationPlugin({
    name: "app1",filename: "remoteEntry.js",exposes: {
      "./Component1": "./src/Component1","./someModule1": "./src/someModule1",})
]

然后是主模块配置:

output: {
  publicPath: "http://localhost:8080/",plugins: [
  new ModuleFederationPlugin({
    name: "mainApp",remotes: {
      app1: "app1@http://localhost:8081/remoteEntry.js"
    }
  })
]

两个模块都部署在生产环境中。

然后我将 Component1app1 更改并部署 app1 模块。

如何处理远程模块缓存?

更新:

在我的例子中,浏览器似乎对 remoteEntry.js 使用了启发式缓存 (https://tools.ietf.org/html/rfc7234#section-4.2.2),因为服务器没有提供明确的过期时间。

因此,当 remoteEntry.js 更新时,主应用程序仍会从缓存中加载该文件,该文件可以缓存数周。 对于块,这不是问题,因为 webpack 可以配置为在文件名中包含哈希。

对于 remoteEntry.js,我看到 2 个选项:

  • 缓存破坏
  • 明确指定缓存控制

你认为这是一条路吗?

解决方法

缓存破坏意味着重新构建(或至少后处理)主应用程序包,这是模块联盟试图避免的问题之一。

因此,考虑到 remoteEntry.js 通常是一个小文件,最好的解决方案是为此文件应用特定的缓存控制,使其永远不会被缓存。

有了nginx,就可以做到:

location ~ .*remoteEntry.js$ {
    expires -1;
    add_header 'Cache-Control' 'no-store,no-cache,must-revalidate,proxy-revalidate,max-age=0';
}
,

在我看来,您永远不应该缓存 remoteEntry.js,因为那是块映射所在的位置。 (这里的映射是指组件和它们的块 url 之间的映射)。您总是希望确保显示最新的远程块。如果映射发生变化(通常只是意味着远程组件更新),浏览器应该获取新的块。

也就是说,您应该使用

缓存破坏块
    output: {
        filename: '[name].[contenthash].js',},plugins: [
        new container.ModuleFederationPlugin({
            name: "RemoteModule",library: { type: "var",name: "RemoteModule" },filename: "remoteEntry.js",exposes: {
                './SuperButton': "./src/components/SuperButton",'./SuperButton2': "./src/components/SuperButton2",shared: {
                react: { singleton: true,eager: true },"react-dom": { singleton: true,}
        }),new HtmlWebpackPlugin({
            template: "./public/index.html"
        })
    ],

在您推荐的webpack.config.js这里https://webpack.js.org/guides/caching/

这种方式,同样,主机将始终尝试获取 remoteEntry.js(一个没有散列的固定 url),并让浏览器在散列更改时获取新的块 url。

,

我不认为这是一个问题,因为 webpack 在构建过程中向应用程序的 js 文件添加了缓存破坏。查看加载应用程序时返回的 HTML 代码,您会注意到每次部署后加载包的标签都不同。 remoteEntry.js 是模块联合方式,允许从远程服务器加载您的应用,而不是您的实际应用代码。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其他元素将获得点击?
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。)
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbcDriver发生异常。为什么?
这是用Java进行XML解析的最佳库。
Java的PriorityQueue的内置迭代器不会以任何特定顺序遍历数据结构。为什么?
如何在Java中聆听按键时移动图像。
Java“Program to an interface”。这是什么意思?
Java在半透明框架/面板/组件上重新绘画。
Java“ Class.forName()”和“ Class.forName()。newInstance()”之间有什么区别?
在此环境中不提供编译器。也许是在JRE而不是JDK上运行?
Java用相同的方法在一个类中实现两个接口。哪种接口方法被覆盖?
Java 什么是Runtime.getRuntime()。totalMemory()和freeMemory()?
java.library.path中的java.lang.UnsatisfiedLinkError否*****。dll
JavaFX“位置是必需的。” 即使在同一包装中
Java 导入两个具有相同名称的类。怎么处理?
Java 是否应该在HttpServletResponse.getOutputStream()/。getWriter()上调用.close()?
Java RegEx元字符(。)和普通点?