使用 create-react-app 脚手架创建的应用,由于 Vue 背景的原因,理所当然的认为默认就有热更新的功能,结果发现并没有,哦对,我想起来了,要在入口文件加入开启的代码,结果发现 state 的值会被重置,看来此事并不简单。
基本配置
开启热更新的总体步骤如下
- 开启热更新
- hot 参数
- HotModuleReplacementPlugin 参数
- 替换根组件
- 版本不同,该方式迭代了很多次,目前 4.8 版本直接 hot(rootComponent) 即可
- 添加 react-hot-loader 来保存组件内部状态
你会发现第一步,脚手架创建的应用都是默认都是开启,这也就是我说在入口文件加入如下代码,也能部分生效的原因
if (module.hot) {
module.hot.accept()
}
react-hot-reload 可以在不丢失 state 数据的情况下热更新 react 组件,注意这里的不丢失 state 数据,才是 react-hot-loader 的核心功能。因此接下来看具体的 react-hot-loader 开启步骤。
配置 react-hot-loader
配置 react-hot-loader 基本步骤
- 第一步安装:react-hot-loader
- babel plugins 添加 react-hot-loader/babel,使得 react 代码支持 HMR(我竟然去掉也可以工作,一定有我没发现的坑???)
- entry 添加 react-hot-loader/patch,为 React 激活 HMR(4.0 版本后可选?只要 react-hot-loader 在 react 之前加载)
- 配置 react-hot-dom,支持 hooks
- typescript 支持需要额外修改么:最新版脚手架创建的无需手动配置
- Code Splitting,动态组件,需要单独用 hot 包裹
在一些搜索博文中,关于 react-hot-loader 的配置一定会提到其提供的 AppContainer 组件,需要使用它来包裹根文件,但其实在最新版中,推荐使用 react-hot-loader/root
下的 hot 函数即可,代码简洁很多,还增加一些额外功能。
已知限制
- 修改 state 初始值,不会更新 state,有 issue ,说是故意设定如此
- 更多不太容易碰到的细节,见 doc