index.js
import _ from 'lodash';
import printMe from './print.js';
import './styles.css';
function component() {
var element = document.createElement('div');
var btn = document.createElement('button');
element.innerHTML = _.join(['Hello', 'webpack'], ' ');
btn.innerHTML = '点击并且检测输出';
btn.onclick = printMe;
element.appendChild(btn);
return element;
}
// document.body.appendChild(component());
let element = component(); // 当 print.js 改变导致页面重新渲染时,重新获取渲染的元素
document.body.appendChild(element);
if (module.hot) {
module.hot.accept('./print.js', function() {
console.log('Accepting the updated printMe module!');
// printMe();
document.body.removeChild(element);
element = component(); // 重新渲染页面后,component 更新 click 事件处理
document.body.appendChild(element);
})
}
if (module.hot) {
module.hot.accept('./print.js', function() {
console.log('接收 the updated printMe module!');
printMe();
})
}
webpack.config.js
const path = require('path');
// HtmlWebpackPlugin 还是会默认生成 index.html 文件。
// 这就是说,它会用新生成的 index.html 文件,把我们的原来的替换。
const HtmlWebpackPlugin = require('html-webpack-plugin');
//通常,在每次构建前清理 /dist 文件夹,是比较推荐的做法,因此只会生成用到的文件。让我们完成这个需求。
// clean-webpack-plugin 是一个比较普及的管理插件,让我们安装和配置下
const CleanWebpackPlugin = require('clean-webpack-plugin');
const webpack = require('webpack');// 热加载需要的 webpack
module.exports = {
entry: {
// app: './src/index.js',
// print: './src/print.js'
app: './src/index.js'
},
devtool: 'inline-source-map',
// 修改配置文件,告诉开发服务器(dev server)在哪里查找文件
devServer: {
contentBase: './dist',
hot: true // 服务器热加载
},
module: {
rules: [
{
test: /\.css$/,
use: ['style-loader', 'css-loader']
}
]
},
plugins: [
// new CleanWebpackPlugin(['dist']),
new HtmlWebpackPlugin({
title: 'Hot Module Replacement'
}),
new webpack.HotModuleReplacementPlugin() // 热加载的插件
],
output: {
filename: '[name].bundle.js',
path: path.resolve(__dirname, 'dist')
}
};
经过一番折腾,发现问题出在HotModuleReplacement(模块热替换)这里。开始以为HMR就是改动了js,会自动编译刷新页面,能够方便开发。结果发现,这是inline参数的作用,并不是HMR。不信你可以把hot插件关掉试试,还是可以实时编译刷新的
var path = require('path');
// var webpack = require('webpack');
module.exports = {
entry: './app/entry.js',
output: {
path: path.resolve(__dirname, "./dist"),
filename: 'bundle.js',
publicPath: "/dist/"
},
devServer: {
// hot: true
},
plugins: [
// new webpack.HotModuleReplacementPlugin()
]
}
bash
$ webpack-dev-server --inline
知道了inline和HMR的区别,那么问题来了,HMR是啥?
目前看了下官方文档,我的理解是:假如一个项目很庞大,打包编译需要很长时间(假设要1min),那么通过HMR,就可以只替换必要的模块(修改过的模块),从而大大减少开发中等待编译的时间?--不知道这样理解对不对?
你的理解是对的。
inline
和HMR
不同,inline
是刷新页面,HMR
是只刷新修改的部分。换句话说,HMR
可以保留页面的状态,这在组件化开发的页面中会很有用。不过在实际开发过程中,不同的状态往往是互相关联的,所以HMR
有时也不好用。但这个思想是比inline
好些的。另外说下如何实现热加载。
1.
npm i webpack-hot-middleware --save-dev
2.修改
entry
3.在entry文件里加上: