这段代码是 Webpack 模块图构建系统 的重要组成部分,
ModuleGraphModule
是每个模块在图中的状态容器,而两个工具函数是为了高效分类模块之间的连接关系,为优化(如 Tree Shaking)和构建性能分析打基础。
ModuleGraphModule
类主要属性说明
-
incomingConnections
- 类型:
SortableSet<ModuleGraphConnection>
- 说明:当前模块的入边连接(谁依赖了我)
- 类型:
-
outgoingConnections
- 类型:
SortableSet<ModuleGraphConnection> | undefined
- 说明:当前模块的出边连接(我依赖了谁)
- 类型:
-
issuer
- 类型:
Module | null | undefined
- 说明:引入该模块的模块(谁把我 import 了)
- 类型:
-
optimizationBailout
- 类型:
(string | OptimizationBailoutFunction)[]
- 说明:记录该模块未被优化的原因(如 Tree Shaking 无效)
- 类型:
-
exports
- 类型:
ExportsInfo
- 说明:模块导出信息(支持 Tree Shaking 和导出分析)
- 类型:
-
preOrderIndex
- 类型:
number | null
- 说明:图遍历时的前序编号(DFS 顺序)
- 类型:
-
postOrderIndex
- 类型:
number | null
- 说明:图遍历时的后序编号(DFS 结束时标号)
- 类型:
-
depth
- 类型:
number | null
- 说明:模块在依赖图中的深度(用于排序优化)
- 类型:
-
profile
- 类型:
ModuleProfile | undefined
- 说明:构建模块时的性能分析信息
- 类型:
-
async
- 类型:
boolean
- 说明:是否是异步模块(如
import()
引入)
- 类型:
-
_unassignedConnections
- 类型:
ModuleGraphConnection[] | undefined
- 说明:尚未归类的连接(构建过程中使用)
- 类型:
工具函数说明
-
getConnectionsByOriginModule(set)
- 输入参数:
SortableSet<ModuleGraphConnection>
- 返回值:
Map<Module | undefined, ModuleGraphConnection[]>
- 说明:按照连接的
originModule
(来源模块)对连接集合进行分组
- 输入参数:
-
getConnectionsByModule(set)
- 输入参数:
SortableSet<ModuleGraphConnection>
- 返回值:
Map<Module | undefined, ModuleGraphConnection[]>
- 说明:按照连接的
module
(目标模块)对连接集合进行分组
类型别名说明
- 输入参数:
-
IncomingConnections
- 实际类型:
SortableSet<ModuleGraphConnection>
- 说明:模块的所有入连接集合(被谁依赖)
- 实际类型:
-
OutgoingConnections
- 实际类型:
SortableSet<ModuleGraphConnection>
- 说明:模块的所有出连接集合(依赖了谁)
- 实际类型:
-
OptimizationBailoutFunction
- 类型定义:一个返回字符串的函数,接收
RequestShortener
- 说明:用于说明模块为什么无法优化(比如缺少静态依赖信息)
- 类型定义:一个返回字符串的函数,接收
js
/** 引入类型定义,用于类型提示(非实际导入,只用于注释) */
/** @typedef {import("./DependenciesBlock")} DependenciesBlock */
/** @typedef {import("./Dependency")} Dependency */
/** @typedef {import("./ExportsInfo").ExportInfo} ExportInfo */
/** @typedef {import("./Module")} Module */
/** @typedef {import("./ModuleProfile")} ModuleProfile */
/** @typedef {import("./RequestShortener")} RequestShortener */
/** @typedef {import("./util/runtime").RuntimeSpec} RuntimeSpec */
/**
* 优化失败回调类型定义。
* 返回一个字符串,用于提示为什么该模块未被优化。
* 可用于 `optimizationBailout` 数组中的元素。
*
* @callback OptimizationBailoutFunction
* @param {RequestShortener} requestShortener - 用于路径简化
* @returns {string} 优化失败原因
*/
const EMPTY_SET = new Set(); // 空集合常量,可复用避免重复创建
/**
* 工具函数:按连接的"来源模块"(originModule)将连接进行分组
*
* @param {SortableSet<ModuleGraphConnection>} set - 输入的模块连接集合
* @returns {readonly Map<Module | undefined, readonly ModuleGraphConnection[]>}
* 返回以"来源模块"为 key、连接数组为 value 的 Map
*/
const getConnectionsByOriginModule = set => {
const map = new Map();
let lastModule = 0; // 缓存上一个处理的模块
let lastList;
for (const connection of set) {
const { originModule } = connection;
// 如果与上一个模块相同,直接向缓存的连接数组中添加
if (lastModule === originModule) {
(lastList).push(connection);
} else {
lastModule = originModule;
const list = map.get(originModule);
if (list !== undefined) {
lastList = list;
list.push(connection);
} else {
const list = [connection];
lastList = list;
map.set(originModule, list);
}
}
}
return map;
};
/**
* 工具函数:按连接的"目标模块"(module)将连接进行分组
*
* @param {SortableSet<ModuleGraphConnection>} set - 输入的模块连接集合
* @returns {readonly Map<Module | undefined, readonly ModuleGraphConnection[]>}
* 返回以"目标模块"为 key、连接数组为 value 的 Map
*/
const getConnectionsByModule = set => {
const map = new Map();
let lastModule = 0;
let lastList;
for (const connection of set) {
const { module } = connection;
if (lastModule === module) {
(lastList).push(connection);
} else {
lastModule = module;
const list = map.get(module);
if (list !== undefined) {
lastList = list;
list.push(connection);
} else {
const list = [connection];
lastList = list;
map.set(module, list);
}
}
}
return map;
};
/** 类型别名:模块图中"指向该模块的连接" */
/** @typedef {SortableSet<ModuleGraphConnection>} IncomingConnections */
/** 类型别名:模块图中"从该模块出发的连接" */
/** @typedef {SortableSet<ModuleGraphConnection>} OutgoingConnections */
/**
* 表示模块图中某个模块的元信息(状态、连接、导出等)
*/
class ModuleGraphModule {
constructor() {
/** @type {IncomingConnections} 当前模块的入边连接(谁依赖我) */
this.incomingConnections = new SortableSet();
/** @type {OutgoingConnections | undefined} 当前模块的出边连接(我依赖谁) */
this.outgoingConnections = undefined;
/** @type {Module | null | undefined} 引入该模块的模块(issuer) */
this.issuer = undefined;
/** @type {(string | OptimizationBailoutFunction)[]} 记录为什么该模块无法被优化 */
this.optimizationBailout = [];
/** @type {ExportsInfo} 当前模块的导出信息(用于 Tree Shaking 等优化) */
this.exports = new ExportsInfo();
/** @type {number | null} 当前模块在图遍历中的"前序遍历索引" */
this.preOrderIndex = null;
/** @type {number | null} 当前模块在图遍历中的"后序遍历索引" */
this.postOrderIndex = null;
/** @type {number | null} 模块在依赖图中的深度(越深优先级越低) */
this.depth = null;
/** @type {ModuleProfile | undefined} 构建该模块时的性能分析数据 */
this.profile = undefined;
/** @type {boolean} 是否为异步模块(通过 import() 等方式引入) */
this.async = false;
/** @type {ModuleGraphConnection[] | undefined} 未分类连接(临时存储) */
this._unassignedConnections = undefined;
}
}