webpack原理篇(五十七):webpack流程:文件生成

Posted 凯小默

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了webpack原理篇(五十七):webpack流程:文件生成相关的知识,希望对你有一定的参考价值。

说明

玩转 webpack 学习笔记

分析 seal 阶段怎么生成文件

我们可以打开 my-project\\node_modules\\webpack\\lib\\Compilation.js 找到 seal 方法

/**
 * @param Callback callback signals when the seal method is finishes
 * @returns void
 */
seal(callback) 
	this.hooks.seal.call();

	while (
		this.hooks.optimizeDependenciesBasic.call(this.modules) ||
		this.hooks.optimizeDependencies.call(this.modules) ||
		this.hooks.optimizeDependenciesAdvanced.call(this.modules)
	) 
		/* empty */
	
	this.hooks.afterOptimizeDependencies.call(this.modules);

	this.hooks.beforeChunks.call();
	for (const preparedEntrypoint of this._preparedEntrypoints) 
		const module = preparedEntrypoint.module;
		const name = preparedEntrypoint.name;
		const chunk = this.addChunk(name);
		const entrypoint = new Entrypoint(name);
		entrypoint.setRuntimeChunk(chunk);
		entrypoint.addOrigin(null, name, preparedEntrypoint.request);
		this.namedChunkGroups.set(name, entrypoint);
		this.entrypoints.set(name, entrypoint);
		this.chunkGroups.push(entrypoint);

		GraphHelpers.connectChunkGroupAndChunk(entrypoint, chunk);
		GraphHelpers.connectChunkAndModule(chunk, module);

		chunk.entryModule = module;
		chunk.name = name;

		this.assignDepth(module);
	
	buildChunkGraph(
		this,
		/** @type Entrypoint[] */ (this.chunkGroups.slice())
	);
	this.sortModules(this.modules);
	this.hooks.afterChunks.call(this.chunks);

	this.hooks.optimize.call();

	while (
		this.hooks.optimizeModulesBasic.call(this.modules) ||
		this.hooks.optimizeModules.call(this.modules) ||
		this.hooks.optimizeModulesAdvanced.call(this.modules)
	) 
		/* empty */
	
	this.hooks.afterOptimizeModules.call(this.modules);

	while (
		this.hooks.optimizeChunksBasic.call(this.chunks, this.chunkGroups) ||
		this.hooks.optimizeChunks.call(this.chunks, this.chunkGroups) ||
		this.hooks.optimizeChunksAdvanced.call(this.chunks, this.chunkGroups)
	) 
		/* empty */
	
	this.hooks.afterOptimizeChunks.call(this.chunks, this.chunkGroups);

	this.hooks.optimizeTree.callAsync(this.chunks, this.modules, err => 
		if (err) 
			return callback(err);
		

		this.hooks.afterOptimizeTree.call(this.chunks, this.modules);

		while (
			this.hooks.optimizeChunkModulesBasic.call(this.chunks, this.modules) ||
			this.hooks.optimizeChunkModules.call(this.chunks, this.modules) ||
			this.hooks.optimizeChunkModulesAdvanced.call(this.chunks, this.modules)
		) 
			/* empty */
		
		this.hooks.afterOptimizeChunkModules.call(this.chunks, this.modules);

		const shouldRecord = this.hooks.shouldRecord.call() !== false;

		this.hooks.reviveModules.call(this.modules, this.records);
		this.hooks.optimizeModuleOrder.call(this.modules);
		this.hooks.advancedOptimizeModuleOrder.call(this.modules);
		this.hooks.beforeModuleIds.call(this.modules);
		this.hooks.moduleIds.call(this.modules);
		this.applyModuleIds();
		this.hooks.optimizeModuleIds.call(this.modules);
		this.hooks.afterOptimizeModuleIds.call(this.modules);

		this.sortItemsWithModuleIds();

		this.hooks.reviveChunks.call(this.chunks, this.records);
		this.hooks.optimizeChunkOrder.call(this.chunks);
		this.hooks.beforeChunkIds.call(this.chunks);
		this.applyChunkIds();
		this.hooks.optimizeChunkIds.call(this.chunks);
		this.hooks.afterOptimizeChunkIds.call(this.chunks);

		this.sortItemsWithChunkIds();

		if (shouldRecord) 
			this.hooks.recordModules.call(this.modules, this.records);
			this.hooks.recordChunks.call(this.chunks, this.records);
		

		this.hooks.beforeHash.call();
		this.createHash();
		this.hooks.afterHash.call();

		if (shouldRecord) 
			this.hooks.recordHash.call(this.records);
		

		this.hooks.beforeModuleAssets.call();
		this.createModuleAssets();
		if (this.hooks.shouldGenerateChunkAssets.call() !== false) 
			this.hooks.beforeChunkAssets.call();
			this.createChunkAssets();
		
		this.hooks.additionalChunkAssets.call(this.chunks);
		this.summarizeDependencies();
		if (shouldRecord) 
			this.hooks.record.call(this, this.records);
		

		this.hooks.additionalAssets.callAsync(err => 
			if (err) 
				return callback(err);
			
			this.hooks.optimizeChunkAssets.callAsync(this.chunks, err => 
				if (err) 
					return callback(err);
				
				this.hooks.afterOptimizeChunkAssets.call(this.chunks);
				this.hooks.optimizeAssets.callAsync(this.assets, err => 
					if (err) 
						return callback(err);
					
					this.hooks.afterOptimizeAssets.call(this.assets);
					if (this.hooks.needAdditionalSeal.call()) 
						this.unseal();
						return this.seal(callback);
					
					return this.hooks.afterSeal.callAsync(callback);
				);
			);
		);
	);

从上面代码可以看到里面做了很多优化工作,另外就是创建 hash

然后进行内容的生成


createModuleAssets 方法

emitAsset 方法

最后 emit 到磁盘

my-project\\node_modules\\webpack\\lib\\Compiler.js

this.hooks.emit.callAsync(compilation, err => 
	if (err) return callback(err);
	outputPath = compilation.getPath(this.outputPath);
	this.outputFileSystem.mkdirp(outputPath, emitFiles);
);

以上是关于webpack原理篇(五十七):webpack流程:文件生成的主要内容,如果未能解决你的问题,请参考以下文章

webpack原理篇(五十六):webpack流程:模块构建和chunk生成阶段

webpack原理篇(五十一):webpack启动过程分析

webpack原理篇(五十四):Tapable是如何和webpack进行关联起来的?

webpack原理篇(五十二):webpack-cli源码阅读

webpack原理篇(五十八):实战开发一个简易的webpack

webpack原理篇(五十三):Tapable插件架构与Hooks设计