前言:
目前,webpack作为前端最流行的项目构建工具,然而webpack内部的执行过程却是黑盒的,作为模块加载和打包神器,只需配置几个文件,加载各种 loader 就可以享受无痛流程化开发,对于 webpack 这样一个复杂度较高的插件集合,我们应该对webpack内部的执行流程进行一定了解,便于我们更好的掌握项目的构建和运行。
工作原理:
基本概念:
- Entry: 入口,webpack构建第一步从entry开始。
- Module:模块,在webpack中一个模块对应一个文件。webpack会从entry开始,递归找出所有依赖的模块。
- Chunk:代码块,一个chunk由多个模块组合而成,用于代码合并与分割。
- Loader: 模块转换器,用于将模块的原内容按照需求转换成新内容。
- Plugin:拓展插件,在webpack构建流程中的特定时机会广播对应的事件,插件可以监听这些事件的发生,在特定的时机做对应的事情。
- Output:输出结果,源码在Webpack中经过一系列处理后而得出的最终结果。
Webpack构建流程:
- 初始化参数
解析 webpack 配置参数,合并 shell 传入和 webpack.config.js 文件配置的参数,形成最后的配置结果。 - 开始编译
上一步得到的参数初始化 compiler 对象,注册所有配置的插件,插件监听 webpack 构建生命周期的事件节点,做出相应的反应,执行对象的 run 方法开始执行编译。 - 确定入口
从配置文件( webpack.config.js )中指定的 entry 入口,开始解析文件构建 AST 语法树,找出依赖,递归下去。 - 编译模块
递归中根据文件类型和 loader 配置,调用所有配置的 loader 对文件进行转换,再找出该模块依赖的模块,再递归本步骤,直到所有入口依赖的文件都经过了本步骤的处理。 - 完成模块编译并输出
递归完后,得到每个文件结果,包含每个模块以及他们之间的依赖关系,根据 entry 配置生成代码块 chunk 。 - 输出完成
输出所有的 chunk 到文件系统。
注意:在构建生命周期中有一系列插件在做合适的时机做合适事情,比如 UglifyPlugin 会在 loader 转换递归完对结果使用 UglifyJs 压缩覆盖之前的结果。
- createAssets : 收集和处理文件的代码;
- createGraph :根据入口文件,返回所有文件依赖图;
- bundle : 根据依赖图整个代码并输出;
webpack.config.js配置:
module.exports = {
entry: '',
output: {
path: '',
filename: '',
publicPath: '',
},
module: {
rules: [
{
test: /\.css?$/,
use: [
'style-loader',
{
loader: 'css-loader',
options: {
// 参数传递
}
}
],
include: [],
exclude: []
}
],
noParse: []
},
plugins: [],
rosolve: {
modules: [],
extensions: [],
alias: []
},
performance: {
hints: '',
maxAssetSize: 20000,
maxEntrypointSize: 40000
},
devTool: '',