move concatenation logic to HarmonyImportSpecifierDependency

This commit is contained in:
Tobias Koppers 2020-09-11 09:41:54 +02:00
parent fc551fa6f3
commit 21e202eb24
2 changed files with 68 additions and 114 deletions

View File

@ -8,6 +8,7 @@
const Dependency = require("../Dependency");
const { UsageState } = require("../ExportsInfo");
const makeSerializable = require("../util/makeSerializable");
const propertyAccess = require("../util/propertyAccess");
const HarmonyImportDependency = require("./HarmonyImportDependency");
/** @typedef {import("webpack-sources").ReplaceSource} ReplaceSource */
@ -251,36 +252,74 @@ HarmonyImportSpecifierDependency.Template = class HarmonyImportSpecifierDependen
*/
apply(dependency, source, templateContext) {
const dep = /** @type {HarmonyImportSpecifierDependency} */ (dependency);
const { moduleGraph, runtime } = templateContext;
const {
moduleGraph,
module,
runtime,
concatenationScope
} = templateContext;
const connection = moduleGraph.getConnection(dep);
// Skip rendering depending when dependency is conditional
if (connection && !connection.isActive(runtime)) return;
super.apply(dependency, source, templateContext);
const {
runtimeTemplate,
module,
initFragments,
runtimeRequirements
} = templateContext;
const ids = dep.getIds(moduleGraph);
const exportExpr = runtimeTemplate.exportFromImport({
moduleGraph,
module: moduleGraph.getModule(dep),
request: dep.request,
exportName: ids,
originModule: module,
asiSafe: dep.shorthand ? true : dep.asiSafe,
isCall: dep.call,
callContext: !dep.directImport,
defaultInterop: true,
importVar: dep.getImportVar(moduleGraph),
initFragments,
runtime,
runtimeRequirements
});
let exportExpr;
if (
concatenationScope &&
concatenationScope.isModuleInScope(connection.module)
) {
if (ids.length === 0) {
exportExpr = concatenationScope.createModuleReference(
connection.module,
{
strict: module.buildMeta.strictHarmonyModule,
asiSafe: dep.asiSafe
}
);
} else if (dep.namespaceObjectAsContext && ids.length === 1) {
exportExpr =
concatenationScope.createModuleReference(connection.module, {
strict: module.buildMeta.strictHarmonyModule,
asiSafe: dep.asiSafe
}) + propertyAccess(ids);
} else {
exportExpr = concatenationScope.createModuleReference(
connection.module,
{
ids,
call: dep.call,
directImport: dep.directImport,
strict: module.buildMeta.strictHarmonyModule,
asiSafe: dep.asiSafe
}
);
}
} else {
super.apply(dependency, source, templateContext);
const {
runtimeTemplate,
initFragments,
runtimeRequirements
} = templateContext;
exportExpr = runtimeTemplate.exportFromImport({
moduleGraph,
module: moduleGraph.getModule(dep),
request: dep.request,
exportName: ids,
originModule: module,
asiSafe: dep.shorthand ? true : dep.asiSafe,
isCall: dep.call,
callContext: !dep.directImport,
defaultInterop: true,
importVar: dep.getImportVar(moduleGraph),
initFragments,
runtime,
runtimeRequirements
});
}
if (dep.shorthand) {
source.insert(dep.range[1], `: ${exportExpr}`);
} else {

View File

@ -12,7 +12,6 @@ const {
ReplaceSource
} = require("webpack-sources");
const ConcatenationScope = require("../ConcatenationScope");
const DependencyTemplate = require("../DependencyTemplate");
const { UsageState } = require("../ExportsInfo");
const Module = require("../Module");
const RuntimeGlobals = require("../RuntimeGlobals");
@ -21,7 +20,6 @@ const HarmonyExportExpressionDependency = require("../dependencies/HarmonyExport
const HarmonyExportImportedSpecifierDependency = require("../dependencies/HarmonyExportImportedSpecifierDependency");
const HarmonyExportSpecifierDependency = require("../dependencies/HarmonyExportSpecifierDependency");
const HarmonyImportDependency = require("../dependencies/HarmonyImportDependency");
const HarmonyImportSpecifierDependency = require("../dependencies/HarmonyImportSpecifierDependency");
const JavascriptParser = require("../javascript/JavascriptParser");
const { equals } = require("../util/ArrayHelpers");
const LazySet = require("../util/LazySet");
@ -966,19 +964,13 @@ class ConcatenatedModule extends Module {
// Create mapping from module to info
const moduleToInfoMap = modulesWithInfoToMap(modulesWithInfo);
// Configure template decorators for dependencies
const innerDependencyTemplates = this._getInnerDependencyTemplates(
dependencyTemplates,
moduleToInfoMap
);
// Generate source code and analyse scopes
// Prepare a ReplaceSource for the final source
for (const info of modulesWithInfo) {
this._analyseModule(
modulesWithInfo,
info,
innerDependencyTemplates,
dependencyTemplates,
runtimeTemplate,
moduleGraph,
chunkGraph,
@ -1453,7 +1445,7 @@ class ConcatenatedModule extends Module {
/**
* @param {ModuleInfo[]} modulesWithInfo modulesWithInfo
* @param {ModuleInfo} info info
* @param {DependencyTemplates} innerDependencyTemplates innerDependencyTemplates
* @param {DependencyTemplates} dependencyTemplates dependencyTemplates
* @param {RuntimeTemplate} runtimeTemplate runtimeTemplate
* @param {ModuleGraph} moduleGraph moduleGraph
* @param {ChunkGraph} chunkGraph chunkGraph
@ -1462,7 +1454,7 @@ class ConcatenatedModule extends Module {
_analyseModule(
modulesWithInfo,
info,
innerDependencyTemplates,
dependencyTemplates,
runtimeTemplate,
moduleGraph,
chunkGraph,
@ -1479,7 +1471,7 @@ class ConcatenatedModule extends Module {
// TODO cache codeGeneration results
const codeGenResult = m.codeGeneration({
dependencyTemplates: innerDependencyTemplates,
dependencyTemplates,
runtimeTemplate,
moduleGraph,
chunkGraph,
@ -1653,27 +1645,6 @@ class ConcatenatedModule extends Module {
return results;
}
/**
* @param {DependencyTemplates} dependencyTemplates outer dependency templates
* @param {Map<Module, ModuleInfo>} moduleToInfoMap map for module info
* @returns {DependencyTemplates} inner dependency templates
*/
_getInnerDependencyTemplates(dependencyTemplates, moduleToInfoMap) {
const innerDependencyTemplates = dependencyTemplates.clone();
innerDependencyTemplates.set(
HarmonyImportSpecifierDependency,
new HarmonyImportSpecifierDependencyConcatenatedTemplate(
dependencyTemplates.get(HarmonyImportSpecifierDependency),
moduleToInfoMap
)
);
// Must use full identifier in our cache here to ensure that the source
// is updated should our dependencies list change.
// TODO webpack 5 refactor
innerDependencyTemplates.updateHash(this.identifier());
return innerDependencyTemplates;
}
findNewName(oldName, usedNamed1, usedNamed2, extraInfo) {
let name = oldName;
@ -1747,60 +1718,4 @@ class ConcatenatedModule extends Module {
makeSerializable(ConcatenatedModule, "webpack/lib/optimize/ConcatenatedModule");
class HarmonyImportSpecifierDependencyConcatenatedTemplate extends DependencyTemplate {
constructor(originalTemplate, modulesMap) {
super();
this.originalTemplate = originalTemplate;
this.modulesMap = modulesMap;
}
/**
* @param {Dependency} dependency the dependency for which the template should be applied
* @param {ReplaceSource} source the current replace source which can be modified
* @param {DependencyTemplateContext} templateContext the context object
* @returns {void}
*/
apply(dependency, source, templateContext) {
const {
moduleGraph,
module: parentModule,
concatenationScope
} = templateContext;
const dep = /** @type {HarmonyImportSpecifierDependency} */ (dependency);
const module = moduleGraph.getModule(dep);
const info = this.modulesMap.get(module);
if (!info) {
this.originalTemplate.apply(dependency, source, templateContext);
return;
}
let content;
const ids = dep.getIds(moduleGraph);
if (ids.length === 0) {
content = concatenationScope.createModuleReference(info.module, {
strict: parentModule.buildMeta.strictHarmonyModule,
asiSafe: dep.asiSafe
});
} else if (dep.namespaceObjectAsContext && ids.length === 1) {
content =
concatenationScope.createModuleReference(info.module, {
strict: parentModule.buildMeta.strictHarmonyModule,
asiSafe: dep.asiSafe
}) + propertyAccess(ids);
} else {
content = concatenationScope.createModuleReference(info.module, {
ids,
call: dep.call,
directImport: dep.directImport,
strict: parentModule.buildMeta.strictHarmonyModule,
asiSafe: dep.asiSafe
});
}
if (dep.shorthand) {
source.insert(dep.range[1], ": " + content);
} else {
source.replace(dep.range[0], dep.range[1] - 1, content);
}
}
}
module.exports = ConcatenatedModule;