首页 文章

Webpack热模块更换反应

提问于
浏览
0

可能是's one of thousands of similar questions, but I still didn't看到有关如何使HMR REALLY 工作的任何答案 .

我做了所有的操作,在docs中描述,在每个答案中你都可以在互联网上找到:

  • 启用webpack-dev-server的"hot"选项

  • 添加 webpack-dev-server/client?{host:port}webpack/hot/only-dev-server 入口点

  • 添加 new webpack.HotModuleReplacementPlugin() 到插件(和NamedModulesPlugin)

  • react-hot-loader文档中的每一步

而现在我拥有 .

假设我的应用程序看起来像这样:

<ReactRouter>
  <App>
    <AppRouter />
  </App>
</ReactRouter>

AppRouter 就像

<Switch>
  <Route path="..." component={Page} />
  ...
</Switch>

Page 只是 <div>some text<div> .

相应的文档,在App模块中我做:

import { hot } from "react-hot-loader"
export default hot(module)(App)

然后尝试将 Page 组件中的文本修改为"new text" .

在控制台中我看到确实启用了HMR:

[WDS] App hot update...
[HMR] Checking for updates on the server...
[HMR] Updated modules:
[HMR]  - ./Page.js
[HMR]  - ./AppRouter.js
[HMR]  - ./App.js
[HMR] App is up to date.

屏幕上的文字确实更新为“新文字” . 到现在为止还挺好 .

然后我再次更新文本到“新文本2”,看到这个:

Ignored an update to unaccepted module ./Page.js -> ./AppRouter.js -> ./App.js
[HMR] The following modules couldn't be hot updated: (They would need a full reload!)
[HMR]  - ./Page.js

react-hot-loader docs中有关于此的 nothing .

但好吧,也许这个文档略有不正确 . 毕竟,webpack自己的文档明确表明我们应该在代码中执行 module.hot.accept(...) .

所以在 App.js 我这样做:

if (module.hot) {
  module.hot.accept("./AppRouter", () => {
    console.log("It works!")
  })
}

然后刷新页面,并尝试再次修改 Page 组件 .

现在控制台说:

[WDS] App hot update...
[HMR] Checking for updates on the server...
App.js:20 It works!
[HMR] Updated modules:
[HMR]  - ./Page.js
[HMR]  - ./AppRouter.js
[HMR]  - ./App.js
[HMR] App is up to date.

text in browser is not updated . 即,HMR已启用但不执行任何操作 .

成功更新说:

[WDS] App hot update...
[HMR] Checking for updates on the server...
[HMR] Updated modules:
[HMR]  - ./Page.js
[HMR] App is up to date.

所以至少我们用 unaccepted changes 修复了以前的错误 - 但是浏览器中仍然没有任何变化 .

当App用 hot(module) 装饰时,我试图做 module.hot.accept(...) ,当它不是 - 结果是相同的时候 .

而且......下一步是什么?我做了我能在官方文档中找到的所有内容,但没有任何成功 . 我究竟做错了什么?

(并请,请't ask 1028036 . It'的所有默认值,相应的例子来自webpack文档 . 不要浪费我的时间在这上面)

1 回答

  • 0

    当您接受文件时,您必须自己做这些事情(例如交换组件) . 那么......像这样:

    if (module.hot) {
      module.hot.accept("./AppRouter", () => {
        const NewAppRouter = require('./AppRouter').default;
        const newApp = (
           <ReactRouter>
              <App>
                 <NewAppRouter />
              </App>
           </ReactRouter>
        );
        ReactDom.render(newApp, container);
      });
    }
    

    这里我会在文件发生变化时收到通知 . 然后我需要更改的文件并使用新文件重新呈现我的应用程序 . 当你使用像redux或mobx这样的状态管理库时,这种方法效果最好,因为当你重新呈现应用程序时,你的应用程序的状态不会改变 .

相关问题