@@ -1918,6 +1918,9 @@ namespace ts {
19181918 return bindParameter ( < ParameterDeclaration > node ) ;
19191919 case SyntaxKind . VariableDeclaration :
19201920 case SyntaxKind . BindingElement :
1921+ if ( ( node as BindingElement ) . dotDotDotToken && node . parent . kind === SyntaxKind . ObjectBindingPattern ) {
1922+ emitFlags |= NodeFlags . HasRestAttribute ;
1923+ }
19211924 return bindVariableDeclarationOrBindingElement ( < VariableDeclaration | BindingElement > node ) ;
19221925 case SyntaxKind . PropertyDeclaration :
19231926 case SyntaxKind . PropertySignature :
@@ -1933,7 +1936,19 @@ namespace ts {
19331936
19341937 case SyntaxKind . SpreadAssignment :
19351938 case SyntaxKind . JsxSpreadAttribute :
1936- emitFlags |= NodeFlags . HasSpreadAttribute ;
1939+ let root = container ;
1940+ let hasRest = false ;
1941+ while ( root . parent ) {
1942+ if ( root . kind === SyntaxKind . ObjectLiteralExpression &&
1943+ root . parent . kind === SyntaxKind . BinaryExpression &&
1944+ ( root . parent as BinaryExpression ) . operatorToken . kind === SyntaxKind . EqualsToken &&
1945+ ( root . parent as BinaryExpression ) . left === root ) {
1946+ hasRest = true ;
1947+ break ;
1948+ }
1949+ root = root . parent ;
1950+ }
1951+ emitFlags |= hasRest ? NodeFlags . HasRestAttribute : NodeFlags . HasSpreadAttribute ;
19371952 return ;
19381953
19391954 case SyntaxKind . CallSignature :
@@ -2544,10 +2559,13 @@ namespace ts {
25442559 const operatorTokenKind = node . operatorToken . kind ;
25452560 const leftKind = node . left . kind ;
25462561
2547- if ( operatorTokenKind === SyntaxKind . EqualsToken
2548- && ( leftKind === SyntaxKind . ObjectLiteralExpression
2549- || leftKind === SyntaxKind . ArrayLiteralExpression ) ) {
2550- // Destructuring assignments are ES6 syntax.
2562+ if ( operatorTokenKind === SyntaxKind . EqualsToken && leftKind === SyntaxKind . ObjectLiteralExpression ) {
2563+ // Destructuring object assignments with are ES2015 syntax
2564+ // and possibly ESNext if they contain rest
2565+ transformFlags |= TransformFlags . AssertESNext | TransformFlags . AssertES2015 | TransformFlags . AssertDestructuringAssignment ;
2566+ }
2567+ else if ( operatorTokenKind === SyntaxKind . EqualsToken && leftKind === SyntaxKind . ArrayLiteralExpression ) {
2568+ // Destructuring assignments are ES2015 syntax.
25512569 transformFlags |= TransformFlags . AssertES2015 | TransformFlags . AssertDestructuringAssignment ;
25522570 }
25532571 else if ( operatorTokenKind === SyntaxKind . AsteriskAsteriskToken
@@ -2581,6 +2599,11 @@ namespace ts {
25812599 transformFlags |= TransformFlags . AssertTypeScript | TransformFlags . ContainsParameterPropertyAssignments ;
25822600 }
25832601
2602+ // parameters with object rest destructuring are ES Next syntax
2603+ if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
2604+ transformFlags |= TransformFlags . AssertESNext ;
2605+ }
2606+
25842607 // If a parameter has an initializer, a binding pattern or a dotDotDot token, then
25852608 // it is ES6 syntax and its container must emit default value assignments or parameter destructuring downlevel.
25862609 if ( subtreeFlags & TransformFlags . ContainsBindingPattern || initializer || dotDotDotToken ) {
@@ -2814,6 +2837,11 @@ namespace ts {
28142837 transformFlags |= TransformFlags . AssertES2017 ;
28152838 }
28162839
2840+ // function declarations with object rest destructuring are ES Next syntax
2841+ if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
2842+ transformFlags |= TransformFlags . AssertESNext ;
2843+ }
2844+
28172845 // If a FunctionDeclaration's subtree has marked the container as needing to capture the
28182846 // lexical this, or the function contains parameters with initializers, then this node is
28192847 // ES6 syntax.
@@ -2851,6 +2879,12 @@ namespace ts {
28512879 transformFlags |= TransformFlags . AssertES2017 ;
28522880 }
28532881
2882+ // function expressions with object rest destructuring are ES Next syntax
2883+ if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
2884+ transformFlags |= TransformFlags . AssertESNext ;
2885+ }
2886+
2887+
28542888 // If a FunctionExpression's subtree has marked the container as needing to capture the
28552889 // lexical this, or the function contains parameters with initializers, then this node is
28562890 // ES6 syntax.
@@ -2888,6 +2922,11 @@ namespace ts {
28882922 transformFlags |= TransformFlags . AssertES2017 ;
28892923 }
28902924
2925+ // arrow functions with object rest destructuring are ES Next syntax
2926+ if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
2927+ transformFlags |= TransformFlags . AssertESNext ;
2928+ }
2929+
28912930 // If an ArrowFunction contains a lexical this, its container must capture the lexical this.
28922931 if ( subtreeFlags & TransformFlags . ContainsLexicalThis ) {
28932932 transformFlags |= TransformFlags . ContainsCapturedLexicalThis ;
@@ -2916,8 +2955,13 @@ namespace ts {
29162955 let transformFlags = subtreeFlags ;
29172956 const nameKind = node . name . kind ;
29182957
2919- // A VariableDeclaration with a binding pattern is ES6 syntax.
2920- if ( nameKind === SyntaxKind . ObjectBindingPattern || nameKind === SyntaxKind . ArrayBindingPattern ) {
2958+ // A VariableDeclaration with an object binding pattern is ES2015 syntax
2959+ // and possibly ESNext syntax if it contains an object binding pattern
2960+ if ( nameKind === SyntaxKind . ObjectBindingPattern ) {
2961+ transformFlags |= TransformFlags . AssertESNext | TransformFlags . AssertES2015 | TransformFlags . ContainsBindingPattern ;
2962+ }
2963+ // A VariableDeclaration with an object binding pattern is ES2015 syntax.
2964+ else if ( nameKind === SyntaxKind . ArrayBindingPattern ) {
29212965 transformFlags |= TransformFlags . AssertES2015 | TransformFlags . ContainsBindingPattern ;
29222966 }
29232967
@@ -3058,14 +3102,17 @@ namespace ts {
30583102 transformFlags |= TransformFlags . AssertJsx ;
30593103 break ;
30603104
3105+ case SyntaxKind . ForOfStatement :
3106+ // for-of might be ESNext if it has a rest destructuring
3107+ transformFlags |= TransformFlags . AssertESNext ;
3108+ // FALLTHROUGH
30613109 case SyntaxKind . NoSubstitutionTemplateLiteral :
30623110 case SyntaxKind . TemplateHead :
30633111 case SyntaxKind . TemplateMiddle :
30643112 case SyntaxKind . TemplateTail :
30653113 case SyntaxKind . TemplateExpression :
30663114 case SyntaxKind . TaggedTemplateExpression :
30673115 case SyntaxKind . ShorthandPropertyAssignment :
3068- case SyntaxKind . ForOfStatement :
30693116 case SyntaxKind . StaticKeyword :
30703117 // These nodes are ES6 syntax.
30713118 transformFlags |= TransformFlags . AssertES2015 ;
@@ -3131,10 +3178,16 @@ namespace ts {
31313178
31323179 case SyntaxKind . SpreadElement :
31333180 case SyntaxKind . SpreadAssignment :
3134- // This node is ES6 or ES future syntax, but is handled by a containing node.
3181+ // This node is ES6 or ES next syntax, but is handled by a containing node.
31353182 transformFlags |= TransformFlags . ContainsSpreadExpression ;
31363183 break ;
31373184
3185+ case SyntaxKind . BindingElement :
3186+ if ( ( node as BindingElement ) . dotDotDotToken ) {
3187+ // this node is ES2015 or ES next syntax, but is handled by a containing node.
3188+ transformFlags |= TransformFlags . ContainsSpreadExpression ;
3189+ }
3190+
31383191 case SyntaxKind . SuperKeyword :
31393192 // This node is ES6 syntax.
31403193 transformFlags |= TransformFlags . AssertES2015 ;
@@ -3147,8 +3200,13 @@ namespace ts {
31473200
31483201 case SyntaxKind . ObjectBindingPattern :
31493202 case SyntaxKind . ArrayBindingPattern :
3150- // These nodes are ES6 syntax.
3151- transformFlags |= TransformFlags . AssertES2015 | TransformFlags . ContainsBindingPattern ;
3203+ // These nodes are ES2015 or ES Next syntax.
3204+ if ( subtreeFlags & TransformFlags . ContainsSpreadExpression ) {
3205+ transformFlags |= TransformFlags . AssertESNext | TransformFlags . ContainsBindingPattern ;
3206+ }
3207+ else {
3208+ transformFlags |= TransformFlags . AssertES2015 | TransformFlags . ContainsBindingPattern ;
3209+ }
31523210 break ;
31533211
31543212 case SyntaxKind . Decorator :
0 commit comments