Skip to content

Commit

Permalink
Merge pull request #10344 from webpack/bugfix/hang-circular-reexport
Browse files Browse the repository at this point in the history
fix hanging build when using circular export *
  • Loading branch information
sokra committed Feb 5, 2020
2 parents 627510d + 614ea54 commit 0b8ef22
Show file tree
Hide file tree
Showing 6 changed files with 55 additions and 8 deletions.
40 changes: 33 additions & 7 deletions lib/FlagDependencyExportsPlugin.js
Expand Up @@ -7,11 +7,9 @@
const Queue = require("./util/Queue");

const addToSet = (a, b) => {
const size = a.size;
for (const item of b) {
a.add(item);
}
return a.size !== size;
};

class FlagDependencyExportsPlugin {
Expand Down Expand Up @@ -58,14 +56,11 @@ class FlagDependencyExportsPlugin {
// break if it should move to the worst state
if (exports === true) {
module.buildMeta.providedExports = true;
notifyDependencies();
return true;
}
// merge in new exports
if (Array.isArray(exports)) {
if (addToSet(moduleProvidedExports, exports)) {
notifyDependencies();
}
addToSet(moduleProvidedExports, exports);
}
// store dependencies
const exportDeps = exportDesc.dependencies;
Expand Down Expand Up @@ -93,6 +88,26 @@ class FlagDependencyExportsPlugin {
}
};

const notifyDependenciesIfDifferent = (set, array) => {
const deps = dependencies.get(module);
if (deps !== undefined) {
if (set.size === array.length) {
let i = 0;
let different = false;
for (const item of set) {
if (item !== array[i++]) {
different = true;
break;
}
}
if (!different) return;
}
for (const dep of deps) {
queue.enqueue(dep);
}
}
};

// Start with all modules without provided exports
for (const module of modules) {
if (module.buildInfo.temporaryProvidedExports) {
Expand All @@ -116,9 +131,20 @@ class FlagDependencyExportsPlugin {
processDependenciesBlock(module);
module.buildInfo.temporaryProvidedExports = providedExportsAreTemporary;
if (!moduleWithExports) {
notifyDependencies();
module.buildMeta.providedExports = true;
} else if (module.buildMeta.providedExports === true) {
notifyDependencies();
} else if (!module.buildMeta.providedExports) {
notifyDependencies();
} else if (module.buildMeta.providedExports !== true) {
module.buildMeta.providedExports = Array.from(
moduleProvidedExports
);
} else {
notifyDependenciesIfDifferent(
moduleProvidedExports,
module.buildMeta.providedExports
);
module.buildMeta.providedExports = Array.from(
moduleProvidedExports
);
Expand Down
6 changes: 5 additions & 1 deletion lib/dependencies/HarmonyExportImportedSpecifierDependency.js
Expand Up @@ -304,9 +304,13 @@ class HarmonyExportImportedSpecifierDependency extends HarmonyImportDependency {
}

if (Array.isArray(importedModule.buildMeta.providedExports)) {
const activeFromOtherStarExports = this._discoverActiveExportsFromOtherStartExports();
return {
exports: importedModule.buildMeta.providedExports.filter(
id => id !== "default"
id =>
id !== "default" &&
!activeFromOtherStarExports.has(id) &&
!this.activeExports.has(id)
),
dependencies: [importedModule]
};
Expand Down
2 changes: 2 additions & 0 deletions test/cases/parsing/harmony-circular-star-reexport/a.js
@@ -0,0 +1,2 @@
export * from "./c";
export const a = "a";
2 changes: 2 additions & 0 deletions test/cases/parsing/harmony-circular-star-reexport/b.js
@@ -0,0 +1,2 @@
export * from "./a";
export const b = "b";
2 changes: 2 additions & 0 deletions test/cases/parsing/harmony-circular-star-reexport/c.js
@@ -0,0 +1,2 @@
export * from "./b";
export const c = "c";
11 changes: 11 additions & 0 deletions test/cases/parsing/harmony-circular-star-reexport/index.js
@@ -0,0 +1,11 @@
import * as all from "./c";

it("should contain all exports", () => {
expect(all).toEqual(
nsObj({
a: "a",
b: "b",
c: "c"
})
);
});

0 comments on commit 0b8ef22

Please sign in to comment.