From 9bce51f651aad297ef9eb6df832bfdaf1de05d84 Mon Sep 17 00:00:00 2001
From: WXL <wl_5969728@163.com>
Date: 星期三, 22 四月 2026 14:27:54 +0800
Subject: [PATCH] 青岛推送

---
 node_modules/webpack/lib/library/ModuleLibraryPlugin.js |  246 ++++++++++++++++++++++++++++++++++++++++++------
 1 files changed, 212 insertions(+), 34 deletions(-)

diff --git a/node_modules/webpack/lib/library/ModuleLibraryPlugin.js b/node_modules/webpack/lib/library/ModuleLibraryPlugin.js
index 065428f..db2d7fe 100644
--- a/node_modules/webpack/lib/library/ModuleLibraryPlugin.js
+++ b/node_modules/webpack/lib/library/ModuleLibraryPlugin.js
@@ -7,11 +7,13 @@
 
 const { ConcatSource } = require("webpack-sources");
 const { UsageState } = require("../ExportsInfo");
+const ExternalModule = require("../ExternalModule");
 const RuntimeGlobals = require("../RuntimeGlobals");
 const Template = require("../Template");
+const HarmonyExportImportedSpecifierDependency = require("../dependencies/HarmonyExportImportedSpecifierDependency");
 const ConcatenatedModule = require("../optimize/ConcatenatedModule");
-const propertyAccess = require("../util/propertyAccess");
-const { getEntryRuntime } = require("../util/runtime");
+const { propertyAccess } = require("../util/property");
+const { getEntryRuntime, getRuntimeKey } = require("../util/runtime");
 const AbstractLibraryPlugin = require("./AbstractLibraryPlugin");
 
 /** @typedef {import("webpack-sources").Source} Source */
@@ -20,22 +22,29 @@
 /** @typedef {import("../../declarations/WebpackOptions").LibraryExport} LibraryExport */
 /** @typedef {import("../Chunk")} Chunk */
 /** @typedef {import("../Compiler")} Compiler */
+/** @typedef {import("../ModuleGraph")} ModuleGraph */
 /** @typedef {import("../Module")} Module */
+/** @typedef {import("../Module").BuildMeta} BuildMeta */
 /** @typedef {import("../Module").RuntimeRequirements} RuntimeRequirements */
 /** @typedef {import("../javascript/JavascriptModulesPlugin").StartupRenderContext} StartupRenderContext */
 /** @typedef {import("../javascript/JavascriptModulesPlugin").ModuleRenderContext} ModuleRenderContext */
+/** @typedef {import("../util/runtime").RuntimeSpec} RuntimeSpec */
+/** @typedef {import("../RuntimeTemplate")} RuntimeTemplate */
 
 /**
+ * Defines the shared type used by this module.
  * @template T
  * @typedef {import("./AbstractLibraryPlugin").LibraryContext<T>} LibraryContext<T>
  */
 
 /**
+ * Defines the module library plugin options type used by this module.
  * @typedef {object} ModuleLibraryPluginOptions
  * @property {LibraryType} type
  */
 
 /**
+ * Defines the module library plugin parsed type used by this module.
  * @typedef {object} ModuleLibraryPluginParsed
  * @property {string} name
  * @property {LibraryExport=} export
@@ -44,11 +53,13 @@
 const PLUGIN_NAME = "ModuleLibraryPlugin";
 
 /**
+ * Represents the module library plugin runtime component.
  * @typedef {ModuleLibraryPluginParsed} T
  * @extends {AbstractLibraryPlugin<ModuleLibraryPluginParsed>}
  */
 class ModuleLibraryPlugin extends AbstractLibraryPlugin {
 	/**
+	 * Creates an instance of ModuleLibraryPlugin.
 	 * @param {ModuleLibraryPluginOptions} options the plugin options
 	 */
 	constructor(options) {
@@ -59,7 +70,7 @@
 	}
 
 	/**
-	 * Apply the plugin
+	 * Applies the plugin by registering its hooks on the compiler.
 	 * @param {Compiler} compiler the compiler instance
 	 * @returns {void}
 	 */
@@ -69,11 +80,36 @@
 		compiler.hooks.thisCompilation.tap(PLUGIN_NAME, (compilation) => {
 			const { onDemandExportsGeneration } =
 				ConcatenatedModule.getCompilationHooks(compilation);
-			onDemandExportsGeneration.tap(PLUGIN_NAME, (_module) => true);
+			onDemandExportsGeneration.tap(
+				PLUGIN_NAME,
+				(module, runtimes, source, finalName) => {
+					/** @type {BuildMeta} */
+					const buildMeta = module.buildMeta || (module.buildMeta = {});
+
+					/** @type {BuildMeta["exportsSourceByRuntime"]} */
+					const exportsSourceByRuntime =
+						buildMeta.exportsSourceByRuntime ||
+						(buildMeta.exportsSourceByRuntime = new Map());
+
+					/** @type {BuildMeta["exportsFinalNameByRuntime"]} */
+					const exportsFinalNameByRuntime =
+						buildMeta.exportsFinalNameByRuntime ||
+						(buildMeta.exportsFinalNameByRuntime = new Map());
+
+					for (const runtime of runtimes) {
+						const key = getRuntimeKey(runtime);
+						exportsSourceByRuntime.set(key, source);
+						exportsFinalNameByRuntime.set(key, finalName);
+					}
+
+					return true;
+				}
+			);
 		});
 	}
 
 	/**
+	 * Finish entry module.
 	 * @param {Module} module the exporting entry module
 	 * @param {string} entryName the name of the entrypoint
 	 * @param {LibraryContext<T>} libraryContext context
@@ -94,8 +130,13 @@
 			exportsInfo.canMangleUse = false;
 		} else {
 			const exportsInfo = moduleGraph.getExportsInfo(module);
-			// If the entry module is commonjs, its exports cannot be mangled
-			if (module.buildMeta && module.buildMeta.treatAsCommonJs) {
+
+			if (
+				// If the entry module is commonjs, its exports cannot be mangled
+				(module.buildMeta && module.buildMeta.treatAsCommonJs) ||
+				// The entry module provides unknown exports
+				exportsInfo._otherExportsInfo.provided === null
+			) {
 				exportsInfo.setUsedInUnknownWay(runtime);
 			} else {
 				exportsInfo.setAllKnownExportsUsed(runtime);
@@ -105,8 +146,9 @@
 	}
 
 	/**
+	 * Returns preprocess as needed by overriding.
 	 * @param {LibraryOptions} library normalized library option
-	 * @returns {T | false} preprocess as needed by overriding
+	 * @returns {T} preprocess as needed by overriding
 	 */
 	parseOptions(library) {
 		const { name } = library;
@@ -123,28 +165,114 @@
 	}
 
 	/**
+	 * Analyze unknown provided exports.
+	 * @param {Source} source source
+	 * @param {Module} module module
+	 * @param {ModuleGraph} moduleGraph moduleGraph
+	 * @param {RuntimeSpec} runtime chunk runtime
+	 * @param {[string, string][]} exports exports
+	 * @param {Set<string>} alreadyRenderedExports already rendered exports
+	 * @returns {ConcatSource} source with null provided exports
+	 */
+	_analyzeUnknownProvidedExports(
+		source,
+		module,
+		moduleGraph,
+		runtime,
+		exports,
+		alreadyRenderedExports
+	) {
+		const result = new ConcatSource(source);
+		/** @type {Set<string>} */
+		const moduleRequests = new Set();
+		/** @type {Map<string, string>} */
+		const unknownProvidedExports = new Map();
+
+		/**
+		 * Resolves dynamic star reexport.
+		 * @param {Module} module the module
+		 * @param {boolean} isDynamicReexport if module is dynamic reexported
+		 */
+		const resolveDynamicStarReexport = (module, isDynamicReexport) => {
+			for (const connection of moduleGraph.getOutgoingConnections(module)) {
+				const dep = connection.dependency;
+
+				// Only handle star-reexport statement
+				if (
+					dep instanceof HarmonyExportImportedSpecifierDependency &&
+					dep.name === null
+				) {
+					const importedModule = connection.resolvedModule;
+					const importedModuleExportsInfo =
+						moduleGraph.getExportsInfo(importedModule);
+
+					// The imported module provides unknown exports
+					// So keep the reexports rendered in the bundle
+					if (
+						dep.getMode(moduleGraph, runtime).type === "dynamic-reexport" &&
+						importedModuleExportsInfo._otherExportsInfo.provided === null
+					) {
+						// Handle export * from 'external'
+						if (importedModule instanceof ExternalModule) {
+							moduleRequests.add(importedModule.userRequest);
+						} else {
+							resolveDynamicStarReexport(importedModule, true);
+						}
+					}
+					// If importer modules existing `dynamic-reexport` dependency
+					// We should keep export statement rendered in the bundle
+					else if (isDynamicReexport) {
+						for (const exportInfo of importedModuleExportsInfo.orderedExports) {
+							if (!exportInfo.provided || exportInfo.name === "default") {
+								continue;
+							}
+							const originalName = exportInfo.name;
+							const usedName = exportInfo.getUsedName(originalName, runtime);
+
+							if (!alreadyRenderedExports.has(originalName) && usedName) {
+								unknownProvidedExports.set(originalName, usedName);
+							}
+						}
+					}
+				}
+			}
+		};
+
+		resolveDynamicStarReexport(module, false);
+
+		for (const request of moduleRequests) {
+			result.add(`export * from "${request}";\n`);
+		}
+
+		for (const [origin, used] of unknownProvidedExports) {
+			exports.push([
+				origin,
+				`${RuntimeGlobals.exports}${propertyAccess([used])}`
+			]);
+		}
+
+		return result;
+	}
+
+	/**
+	 * Renders source with library export.
 	 * @param {Source} source source
 	 * @param {Module} module module
 	 * @param {StartupRenderContext} renderContext render context
 	 * @param {LibraryContext<T>} libraryContext context
 	 * @returns {Source} source with library export
 	 */
-	renderStartup(
-		source,
-		module,
-		{
+	renderStartup(source, module, renderContext, { options, compilation }) {
+		const {
 			moduleGraph,
 			chunk,
 			codeGenerationResults,
 			inlined,
 			inlinedInIIFE,
 			runtimeTemplate
-		},
-		{ options, compilation }
-	) {
-		const result = new ConcatSource(source);
-
-		const exportsInfo = options.export
+		} = renderContext;
+		let result = new ConcatSource(source);
+		const exportInfos = options.export
 			? [
 					moduleGraph.getExportInfo(
 						module,
@@ -152,19 +280,46 @@
 					)
 				]
 			: moduleGraph.getExportsInfo(module).orderedExports;
-		const definitions =
-			inlined && !inlinedInIIFE
-				? (module.buildMeta && module.buildMeta.exportsFinalName) || {}
-				: {};
+
+		const exportsFinalNameByRuntime =
+			(module.buildMeta &&
+				module.buildMeta.exportsFinalNameByRuntime &&
+				module.buildMeta.exportsFinalNameByRuntime.get(
+					getRuntimeKey(chunk.runtime)
+				)) ||
+			{};
+
+		const isInlinedEntryWithoutIIFE = inlined && !inlinedInIIFE;
+		// Direct export bindings from on-demand concatenation
+		const definitions = isInlinedEntryWithoutIIFE
+			? exportsFinalNameByRuntime
+			: {};
+
 		/** @type {string[]} */
 		const shortHandedExports = [];
 		/** @type {[string, string][]} */
 		const exports = [];
+		/** @type {Set<string>} */
+		const alreadyRenderedExports = new Set();
+
 		const isAsync = moduleGraph.isAsync(module);
 
 		const treatAsCommonJs =
 			module.buildMeta && module.buildMeta.treatAsCommonJs;
 		const skipRenderDefaultExport = Boolean(treatAsCommonJs);
+
+		const moduleExportsInfo = moduleGraph.getExportsInfo(module);
+
+		// Define ESM compatibility flag will rely on `__webpack_exports__`
+		const needHarmonyCompatibilityFlag =
+			moduleExportsInfo.otherExportsInfo.getUsed(chunk.runtime) !==
+				UsageState.Unused ||
+			moduleExportsInfo
+				.getReadOnlyExportInfo("__esModule")
+				.getUsed(chunk.runtime) !== UsageState.Unused;
+
+		let needExportsDeclaration =
+			!isInlinedEntryWithoutIIFE || isAsync || needHarmonyCompatibilityFlag;
 
 		if (isAsync) {
 			result.add(
@@ -172,17 +327,18 @@
 			);
 		}
 
-		outer: for (const exportInfo of exportsInfo) {
+		// Try to find all known exports of the entry module
+		outer: for (const exportInfo of exportInfos) {
 			if (!exportInfo.provided) continue;
 
 			const originalName = exportInfo.name;
-
+			// Skip rendering the default export in some cases
 			if (skipRenderDefaultExport && originalName === "default") continue;
 
+			// Try to find all exports from the reexported modules
 			const target = exportInfo.findTarget(moduleGraph, (_m) => true);
 			if (target) {
 				const reexportsInfo = moduleGraph.getExportsInfo(target.module);
-
 				for (const reexportInfo of reexportsInfo.orderedExports) {
 					if (
 						reexportInfo.provided === false &&
@@ -199,14 +355,16 @@
 				(exportInfo.getUsedName(originalName, chunk.runtime));
 			/** @type {string | undefined} */
 			const definition = definitions[usedName];
-
 			/** @type {string | undefined} */
 			let finalName;
 
 			if (definition) {
 				finalName = definition;
 			} else {
+				// Fallback to `__webpack_exports__` property access
+				// when no direct export binding was found
 				finalName = `${RuntimeGlobals.exports}${Template.toIdentifier(originalName)}`;
+				needExportsDeclaration = true;
 				result.add(
 					`${runtimeTemplate.renderConst()} ${finalName} = ${RuntimeGlobals.exports}${propertyAccess(
 						[usedName]
@@ -215,6 +373,7 @@
 			}
 
 			if (
+				// If the name includes `property access` and `call expressions`
 				finalName &&
 				(finalName.includes(".") ||
 					finalName.includes("[") ||
@@ -245,9 +404,13 @@
 						: `${finalName} as ${originalName}`
 				);
 			}
+
+			alreadyRenderedExports.add(originalName);
 		}
 
+		// Add default export `__webpack_exports__` statement to keep better compatibility
 		if (treatAsCommonJs) {
+			needExportsDeclaration = true;
 			shortHandedExports.push(`${RuntimeGlobals.exports} as default`);
 		}
 
@@ -255,36 +418,51 @@
 			result.add(`export { ${shortHandedExports.join(", ")} };\n`);
 		}
 
+		result = this._analyzeUnknownProvidedExports(
+			result,
+			module,
+			moduleGraph,
+			chunk.runtime,
+			exports,
+			alreadyRenderedExports
+		);
+
 		for (const [exportName, final] of exports) {
 			result.add(
 				`export ${runtimeTemplate.renderConst()} ${exportName} = ${final};\n`
 			);
 		}
 
+		if (!needExportsDeclaration) {
+			renderContext.needExportsDeclaration = false;
+		}
+
 		return result;
 	}
 
 	/**
+	 * Renders module content.
 	 * @param {Source} source source
 	 * @param {Module} module module
 	 * @param {ModuleRenderContext} renderContext render context
-	 * @param {Omit<LibraryContext<T>, 'options'>} libraryContext context
+	 * @param {Omit<LibraryContext<T>, "options">} libraryContext context
 	 * @returns {Source} source with library export
 	 */
 	renderModuleContent(
 		source,
 		module,
-		{ factory, inlinedInIIFE },
+		{ factory, inlinedInIIFE, chunk },
 		libraryContext
 	) {
-		// Re-add `factoryExportsBinding` to the source
-		// when the module is rendered as a factory or treated as an inlined (startup) module but wrapped in an IIFE
-		if (
-			(inlinedInIIFE || factory) &&
+		const exportsSource =
 			module.buildMeta &&
-			module.buildMeta.factoryExportsBinding
-		) {
-			return new ConcatSource(module.buildMeta.factoryExportsBinding, source);
+			module.buildMeta.exportsSourceByRuntime &&
+			module.buildMeta.exportsSourceByRuntime.get(getRuntimeKey(chunk.runtime));
+
+		// Re-add the module's exports source when rendered in factory
+		// or as an inlined startup module wrapped in an IIFE
+		if ((inlinedInIIFE || factory) && exportsSource) {
+			return new ConcatSource(exportsSource, source);
 		}
 		return source;
 	}

--
Gitblit v1.9.3