Skip to content
This repository has been archived by the owner on Apr 9, 2022. It is now read-only.

Commit

Permalink
fix(@angular-devkit/build-optimizer): correct 2.8 enum export assignment
Browse files Browse the repository at this point in the history
  • Loading branch information
clydin authored and filipesilva committed May 17, 2018
1 parent 785c0b8 commit c13af1d
Show file tree
Hide file tree
Showing 3 changed files with 61 additions and 20 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ describe('build-optimizer', () => {
ChangeDetectionStrategy[ChangeDetectionStrategy["OnPush"] = 0] = "OnPush";
ChangeDetectionStrategy[ChangeDetectionStrategy["Default"] = 1] = "Default";
return ChangeDetectionStrategy;
})(ChangeDetectionStrategy || (ChangeDetectionStrategy = {}));
})({});
var Clazz = /*@__PURE__*/ (function () { function Clazz() { } ${staticProperty} return Clazz; }());
var ComponentClazz = /*@__PURE__*/ (function () {
function ComponentClazz() { }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,8 @@ function visitBlockStatements(
// update IIFE and replace variable statement and old IIFE
updatedStatements.splice(uIndex, 2, updateEnumIife(
currentStatement,
iife,
iife[0],
iife[1],
));
// skip IIFE statement
oIndex++;
Expand Down Expand Up @@ -158,7 +159,10 @@ function visitBlockStatements(
}

// TS 2.3 enums have statements that are inside a IIFE.
function findTs2_3EnumIife(name: string, statement: ts.Statement): ts.CallExpression | null {
function findTs2_3EnumIife(
name: string,
statement: ts.Statement,
): [ts.CallExpression, ts.Expression | undefined] | null {
if (!ts.isExpressionStatement(statement)) {
return null;
}
Expand All @@ -173,6 +177,7 @@ function findTs2_3EnumIife(name: string, statement: ts.Statement): ts.CallExpres
}

const callExpression = expression;
let exportExpression;

let argument = expression.arguments[0];
if (!ts.isBinaryExpression(argument)) {
Expand All @@ -183,12 +188,14 @@ function findTs2_3EnumIife(name: string, statement: ts.Statement): ts.CallExpres
return null;
}

let potentialExport = false;
if (argument.operatorToken.kind === ts.SyntaxKind.FirstAssignment) {
if (!ts.isBinaryExpression(argument.right)
|| argument.right.operatorToken.kind !== ts.SyntaxKind.BarBarToken) {
return null;
}

potentialExport = true;
argument = argument.right;
}

Expand All @@ -200,6 +207,10 @@ function findTs2_3EnumIife(name: string, statement: ts.Statement): ts.CallExpres
return null;
}

if (potentialExport && !ts.isIdentifier(argument.left)) {
exportExpression = argument.left;
}

expression = expression.expression;
while (ts.isParenthesizedExpression(expression)) {
expression = expression.expression;
Expand Down Expand Up @@ -264,7 +275,7 @@ function findTs2_3EnumIife(name: string, statement: ts.Statement): ts.CallExpres
}
}

return callExpression;
return [callExpression, exportExpression];
}

// TS 2.2 enums have statements after the variable declaration, with index statements followed
Expand Down Expand Up @@ -362,9 +373,22 @@ function findEnumNameStatements(
return enumStatements;
}

function updateHostNode(hostNode: ts.VariableStatement, expression: ts.Expression): ts.Statement {
function addPureComment<T extends ts.Node>(node: T): T {
const pureFunctionComment = '@__PURE__';

return ts.addSyntheticLeadingComment(
node,
ts.SyntaxKind.MultiLineCommentTrivia,
pureFunctionComment,
false,
);
}

function updateHostNode(
hostNode: ts.VariableStatement,
expression: ts.Expression,
): ts.Statement {

// Update existing host node with the pure comment before the variable declaration initializer.
const variableDeclaration = hostNode.declarationList.declarations[0];
const outerVarStmt = ts.updateVariableStatement(
Expand All @@ -377,12 +401,7 @@ function updateHostNode(hostNode: ts.VariableStatement, expression: ts.Expressio
variableDeclaration,
variableDeclaration.name,
variableDeclaration.type,
ts.addSyntheticLeadingComment(
expression,
ts.SyntaxKind.MultiLineCommentTrivia,
pureFunctionComment,
false,
),
expression,
),
],
),
Expand All @@ -391,12 +410,22 @@ function updateHostNode(hostNode: ts.VariableStatement, expression: ts.Expressio
return outerVarStmt;
}

function updateEnumIife(hostNode: ts.VariableStatement, iife: ts.CallExpression): ts.Statement {
function updateEnumIife(
hostNode: ts.VariableStatement,
iife: ts.CallExpression,
exportAssignment?: ts.Expression,
): ts.Statement {
if (!ts.isParenthesizedExpression(iife.expression)
|| !ts.isFunctionExpression(iife.expression.expression)) {
throw new Error('Invalid IIFE Structure');
}

// Ignore export assignment if variable is directly exported
if (hostNode.modifiers
&& hostNode.modifiers.findIndex(m => m.kind == ts.SyntaxKind.ExportKeyword) != -1) {
exportAssignment = undefined;
}

const expression = iife.expression.expression;
const updatedFunction = ts.updateFunctionExpression(
expression,
Expand All @@ -415,17 +444,29 @@ function updateEnumIife(hostNode: ts.VariableStatement, iife: ts.CallExpression)
),
);

let arg: ts.Expression = ts.createObjectLiteral();
if (exportAssignment) {
arg = ts.createBinary(exportAssignment, ts.SyntaxKind.BarBarToken, arg);
}
const updatedIife = ts.updateCall(
iife,
ts.updateParen(
iife.expression,
updatedFunction,
),
iife.typeArguments,
iife.arguments,
[arg],
);

return updateHostNode(hostNode, updatedIife);
let value: ts.Expression = addPureComment(updatedIife);
if (exportAssignment) {
value = ts.createBinary(
exportAssignment,
ts.SyntaxKind.FirstAssignment,
updatedIife);
}

return updateHostNode(hostNode, value);
}

function createWrappedEnum(
Expand All @@ -450,5 +491,5 @@ function createWrappedEnum(
innerReturn,
]);

return updateHostNode(hostNode, ts.createParen(iife));
return updateHostNode(hostNode, addPureComment(ts.createParen(iife)));
}
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ describe('wrap-enums', () => {
ChangeDetectionStrategy[ChangeDetectionStrategy["OnPush"] = 0] = "OnPush";
ChangeDetectionStrategy[ChangeDetectionStrategy["Default"] = 1] = "Default";
return ChangeDetectionStrategy;
})(ChangeDetectionStrategy || (ChangeDetectionStrategy = {}));
})({});
`;

expect(tags.oneLine`${transform(input)}`).toEqual(tags.oneLine`${output}`);
Expand All @@ -73,7 +73,7 @@ describe('wrap-enums', () => {
AnimatorControlState[AnimatorControlState["FINISHED"] = 3] = "FINISHED";
AnimatorControlState[AnimatorControlState["DESTROYED"] = 4] = "DESTROYED";
return AnimatorControlState;
})(AnimatorControlState || (AnimatorControlState = {}));
})({});
`;

expect(tags.oneLine`${transform(input)}`).toEqual(tags.oneLine`${output}`);
Expand Down Expand Up @@ -155,7 +155,7 @@ describe('wrap-enums', () => {
RequestMethod[RequestMethod["Head"] = 5] = "Head";
RequestMethod[RequestMethod["Patch"] = 6] = "Patch";
return RequestMethod;
})(RequestMethod || (RequestMethod = {}));
})({});
`;

expect(tags.oneLine`${transform(input)}`).toEqual(tags.oneLine`${output}`);
Expand All @@ -171,12 +171,12 @@ describe('wrap-enums', () => {
})(ExportEnum = exports.ExportEnum || (exports.ExportEnum = {}));
`;
const output = tags.stripIndent`
var ExportEnum = /*@__PURE__*/ (function (ExportEnum) {
var ExportEnum = exports.ExportEnum = /*@__PURE__*/ (function (ExportEnum) {
ExportEnum[ExportEnum["A"] = 0] = "A";
ExportEnum[ExportEnum["B"] = 1] = "B";
ExportEnum[ExportEnum["C"] = 2] = "C";
return ExportEnum;
})(ExportEnum = exports.ExportEnum || (exports.ExportEnum = {}));
})(exports.ExportEnum || {});
`;

expect(tags.oneLine`${transform(input)}`).toEqual(tags.oneLine`${output}`);
Expand Down

0 comments on commit c13af1d

Please sign in to comment.