Webpack 构建流程

面试题

Q:请简述 Webpack 的构建流程?

一、核心流程

Webpack 的构建过程可以概括为:

读取配置 → 创建 Compiler → 构建模块依赖图
→ 生成 Chunk → 优化并生成 Assets → 输出文件

1. 初始化

Webpack 读取配置文件、命令行参数和默认配置,得到最终配置并创建 Compiler

2. 构建模块依赖图

Webpack 从 entry 入口开始:

  1. 通过 Resolver 解析模块路径;
  2. 分析 importrequireimport() 等依赖;
  3. 递归处理依赖模块,最终形成 ModuleGraph

模块依赖图记录模块之间的引用关系,是后续生成 Chunk 和进行优化的基础。

3. 生成 Chunk

Webpack 根据入口和动态 import() 生成 Chunk,并根据拆分策略提取公共模块。

  • 静态 import 通常属于当前依赖链;
  • 动态 import() 会形成异步 Chunk,实现代码分割;
  • 一个 Chunk 最终可能生成 JS、CSS、Source Map 等多个 Asset。

4. 优化并输出

Webpack 会在生成 Chunk 后执行常见优化:

  • Tree Shaking:删除未使用的 ESM 导出;
  • Scope Hoisting:合并模块作用域;
  • SplitChunks:提取公共依赖;
  • 压缩代码并生成 Runtime。

之后通过 processAssets 处理最终资源,再将资源写入 output 配置指定的目录。

二、Compiler 和 Compilation

  • Compiler:代表整个 Webpack 编译环境,负责调度完整生命周期。
  • Compilation:代表一次具体的构建,包含本次构建的模块、Chunk、Asset、错误和警告。

普通构建通常产生一次 Compilation。Watch 模式下,同一个 Compiler 会因为文件变化产生多次 Compilation。

三、常见追问

Q:为什么动态import() 可以实现代码分割?

Webpack 会把动态 import() 识别为异步边界,为它生成独立 Chunk,运行时再按需加载该文件。

Q:Tree Shaking 和 SplitChunks 有什么区别?

  • Tree Shaking:删除模块中没有使用的代码;
  • SplitChunks:重新拆分模块,提取公共依赖。

Q:Watch 模式每次都会重新创建 Compiler 吗?

不会。Watch 模式通常复用同一个 Compiler,在文件变化后重新创建 Compilation,并尽量利用缓存只处理受影响的部分。

四、面试回答模板

Webpack 首先读取配置并创建 Compiler,然后从 Entry 出发,通过 Resolver 解析模块,分析模块依赖并递归构建模块依赖图。接着根据入口和动态 import 生成 Chunk,执行 Tree Shaking、SplitChunks 等优化,生成最终的 JS、CSS 等 Assets,最后输出到指定目录。