Fix export bindings not updated by 'for...in' and 'for...of' (#11074)
* Correctly transpile export bindings for some for-of loops * Correctly transform non-destructured for of loops to update exported variables * Add tests * Don't replace entire for of loop * Correctly transform destructured for-of/for-in exports * Update exported variables in array pattern and more fixes * Refresh test output * Update tests and rebase on master * Refactor ForOf|ForIn visitor * Don't transform re-declared exported vars * Generate better name for loop id Co-Authored-By: Nicolò Ribaudo <nicolo.ribaudo@gmail.com> * Idiomatically generate UidIdentifier * Update scope after replacing loop declaration Co-authored-by: Nicolò Ribaudo <nicolo.ribaudo@gmail.com>
This commit is contained in:
committed by
Nicolò Ribaudo
parent
5aa368cec1
commit
dadba01249
@@ -306,4 +306,40 @@ const rewriteReferencesVisitor = {
|
||||
}
|
||||
},
|
||||
},
|
||||
"ForOfStatement|ForInStatement"(path) {
|
||||
const { scope, node } = path;
|
||||
const { left } = node;
|
||||
const { exported, scope: programScope } = this;
|
||||
|
||||
if (!t.isVariableDeclaration(left)) {
|
||||
let didTransform = false;
|
||||
const bodyPath = path.get("body");
|
||||
const loopBodyScope = bodyPath.scope;
|
||||
for (const name of Object.keys(t.getOuterBindingIdentifiers(left))) {
|
||||
if (
|
||||
exported.get(name) &&
|
||||
programScope.getBinding(name) === scope.getBinding(name)
|
||||
) {
|
||||
didTransform = true;
|
||||
if (loopBodyScope.hasOwnBinding(name)) {
|
||||
loopBodyScope.rename(name);
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!didTransform) {
|
||||
return;
|
||||
}
|
||||
const newLoopId = scope.generateUidIdentifierBasedOnNode(left);
|
||||
bodyPath.unshiftContainer(
|
||||
"body",
|
||||
t.expressionStatement(t.assignmentExpression("=", left, newLoopId)),
|
||||
);
|
||||
path
|
||||
.get("left")
|
||||
.replaceWith(
|
||||
t.variableDeclaration("let", [t.variableDeclarator(newLoopId)]),
|
||||
);
|
||||
scope.registerDeclaration(path.get("left"));
|
||||
}
|
||||
},
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user