webpack-dev-server与热加载插件整合设置 HMR 实现局部刷新的2种方式
[toc]
巨详细文档说明-各种情况都有考虑
本文将讲 react-hot-loader
-v3 与 webpack-dev-server
-v2.2 整合的那些关键点(这个版本适用于开发环境)。 后续会补上 express
与 webpack-dev-middleware
、webpack-hot-middleware
的版本(这个版本适用于生产环境)。
本文与 redbox-react
一起讲.
1. 利用 react-hot-loader 3
1.1. 与redbox-react
整合的例子
The react-hot-loader example features the upcoming version 3 (currently 3.0.0-beta.2), but does not yet support error catching and rendering on updates, only on initial mount. This is the future, but it's not quite here.
1.2. 官方文档Hot Module Replacement - React
1.3.1. 注意-1
webpack-dev-server 必须开启 2 种 hot server!!!!
- 一个 由 属性
devServer.hot: true
控制(即entry: 'webpack/hot/dev-server'
) 使用dev-server.js
. - 另一个 由
entry: 'webpack/hot/only-dev-server'
控制 使用only-dev-server.js
加上 react-hot-loader
的 'react-hot-loader/patch' 就是3个。
1.3.2. 注意-2
若 devServer.publicPath
有设置,则其值 必须也建议 与 output.publicPath
一样。 若不一样,则
- 与
index.html
中的bundle.js
的引入地址src="/build/bundle.js"
中的/build/
部分必须保持一致, 否则网页会找不到bundle.js
,因为此时的正确地址为:devServer.publicPath
+ bundle.js。 也就是说,devServer.publicPath
覆盖了output.publicPath
。- 1.1. 但这还是会导致再热加载时,本应该
局部替换页面不刷新
的情况变成页面整体刷新
!!! 因为output.publicPath
// necessary for HMR to know where to load the hot update chunks
- 1.1. 但这还是会导致再热加载时,本应该
导致再热加载时,本应该局部替换页面不刷新
的情况变成页面整体刷新
的失误配置点
- 在正确设置好局部替换页面不刷新热加载相关配置后,又去设置了
devServer.watchContentBase = true
。 index.html
中的bundle.js
的引入地址src="/build/bundle.js"
中的/build/
部分 与output.publicPath
值不一致。devServer.hot
没有设置为true
。
1.4. 配置注意事项
//.babelrc
"presets": [
["latest", { // 注意这里的书写格式
"es2015": {
"loose": true,
"modules": false
}
}],
"stage-1",
"react"
],
// 在配置文件没做好 分环境 考虑设置时,这个必须
"plugins": ["react-hot-loader/babel"],
// 用于已分好 开发环境用
"env": {
"development": {
"plugins": [
"react-hot-loader/babel"
]
}
}
const render = (Component) => {
ReactDOM.render(
,
// document.querySelector('#container'),
document.getElementById('container'),
)
}
render(App) // 不能省
if (module.hot) {
console.log(module.hot)
// module.hot.accept('components/App', () => {
module.hot.accept((err) => { // 地址参数可以省去
if (err) {
console.error('Cannot apply hot update', err)
}
render(App)
})
}
devServer: {
hot: true, // 使用'webpack/hot/dev-server'
// watchContentBase: true, // 会引起整个页面刷新
// 这项可有可无
watchOptions: {
aggregateTimeout: 300, // rebuild 延时, wait so long for more changes
ignored: /node_modules/,
poll: 1000, // 设置检测文件变化的间隔时间段,Check for changes every second
},
}
2. 利用 babel-plugin-react-transform - 不推荐
与redbox-react
整合的例子
The react-transform-catch-errors example shows how to catch and render errors with the deprecated react-transform-catch-errors plugin. This is the way of the past, but it works today.
添加React Transform支持
Babel-plugin-react-transform
已经过时了,开发者也宣布已经停止维护
"env": {
"development": {
"presets": [
"react-hmre"
],
"plugins": [
"react-hot-loader/babel",
["react-transform", {
"transforms": [{
"transform": "react-transform-hmr",
"imports": ["react"],
"locals": ["module"]
}, {
"transform": "react-transform-catch-errors",
"imports": ["react", "redbox-react", "../reporterOptions.js"]
}],
"factoryMethods": ["React.createClass", "createClass"]
}]
]
}
}