Parenthesize export assignments if needed (#19590)

* parenthesize export assignments if needed

* Add default-specific parenthesization to handle lookahead

* New parenthesization logic for export default

* Handle commalist and comma cases
This commit is contained in:
Wesley Wigham
2017-10-30 18:23:32 -07:00
committed by GitHub
parent a89c055a48
commit c2aa13dac5
11 changed files with 350 additions and 3 deletions

View File

@@ -1982,7 +1982,7 @@ namespace ts {
node.decorators = asNodeArray(decorators);
node.modifiers = asNodeArray(modifiers);
node.isExportEquals = isExportEquals;
node.expression = expression;
node.expression = isExportEquals ? parenthesizeBinaryOperand(SyntaxKind.EqualsToken, expression, /*isLeftSideOfBinary*/ false, /*leftOperand*/ undefined) : parenthesizeDefaultExpression(expression);
return node;
}
@@ -3885,6 +3885,27 @@ namespace ts {
: e;
}
/**
* [Per the spec](https://tc39.github.io/ecma262/#prod-ExportDeclaration), `export default` accepts _AssigmentExpression_ but
* has a lookahead restriction for `function`, `async function`, and `class`.
*
* Basically, that means we need to parenthesize in the following cases:
*
* - BinaryExpression of CommaToken
* - CommaList (synthetic list of multiple comma expressions)
* - FunctionExpression
* - ClassExpression
*/
export function parenthesizeDefaultExpression(e: Expression) {
const check = skipPartiallyEmittedExpressions(e);
return (check.kind === SyntaxKind.ClassExpression ||
check.kind === SyntaxKind.FunctionExpression ||
check.kind === SyntaxKind.CommaListExpression ||
isBinaryExpression(check) && check.operatorToken.kind === SyntaxKind.CommaToken)
? createParen(e)
: e;
}
/**
* Wraps an expression in parentheses if it is needed in order to use the expression
* as the expression of a NewExpression node.