diff --git a/features.txt b/features.txt index e85ecc3f18..99e7e0dead 100644 --- a/features.txt +++ b/features.txt @@ -272,6 +272,10 @@ Intl.DurationFormat # https://github.com/tc39/proposal-regexp-set-notation regexp-v-flag +# Decorators +# https://github.com/tc39/proposal-decorators +decorators + ## Standard language features # # Language features that have been included in a published version of the diff --git a/src/class-elements/field-definition-accessor-no-line-terminator.case b/src/class-elements/field-definition-accessor-no-line-terminator.case new file mode 100644 index 0000000000..3f22404108 --- /dev/null +++ b/src/class-elements/field-definition-accessor-no-line-terminator.case @@ -0,0 +1,28 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +desc: Valid accessor FieldDefinition, ClassElementName, PropertyName Syntax +info: | + FieldDefinition[Yield, Await] : + accessor [no LineTerminator here] ClassElementName[?Yield, ?Await] Initializer[+In, ?Yield, ?Await]opt + +template: default +features: [decorators] +---*/ + +//- elements +accessor +$; +static accessor +$; + +//- assertions +let c = new C(); + +assert.sameValue(Object.hasOwnProperty.call(C.prototype, 'accessor'), false); +assert.sameValue(Object.hasOwnProperty.call(C.prototype, '$'), false); +assert.sameValue(Object.hasOwnProperty.call(C, 'accessor'), true); +assert.sameValue(Object.hasOwnProperty.call(C, '$'), true); +assert.sameValue(Object.hasOwnProperty.call(c, 'accessor'), true); +assert.sameValue(Object.hasOwnProperty.call(c, '$'), true); diff --git a/src/class-elements/grammar-field-accessor.case b/src/class-elements/grammar-field-accessor.case new file mode 100644 index 0000000000..be8792e8ac --- /dev/null +++ b/src/class-elements/grammar-field-accessor.case @@ -0,0 +1,21 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +desc: Valid accessor FieldDefinition, ClassElementName, PropertyName Syntax +info: | + FieldDefinition[Yield, Await] : + ClassElementName[?Yield, ?Await] Initializer[+In, ?Yield, ?Await]opt + accessor [no LineTerminator here] ClassElementName[?Yield, ?Await] Initializer[+In, ?Yield, ?Await]opt + +template: syntax/valid +features: [decorators] +---*/ + +//- elements +accessor $; +accessor _; +accessor \u{6F}; +accessor \u2118; +accessor ZW_\u200C_NJ; +accessor ZW_\u200D_J; diff --git a/src/decorator/decorator-call-expr-identifier-reference.case b/src/decorator/decorator-call-expr-identifier-reference.case new file mode 100644 index 0000000000..e644f75627 --- /dev/null +++ b/src/decorator/decorator-call-expr-identifier-reference.case @@ -0,0 +1,44 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +desc: > + Decorator @ DecoratorCallExpression +info: | + DecoratorCallExpression[Yield, Await] : + DecoratorMemberExpression[?Yield, ?Await] Arguments[?Yield, ?Await] + + DecoratorMemberExpression[Yield, Await] : + IdentifierReference[?Yield, ?Await] + PrivateIdentifier + DecoratorMemberExpression[?Yield, ?Await] . IdentifierName + + IdentifierReference[Yield, Await] : + Identifier + [~Yield] yield + [~Await] await + +template: syntax/valid +---*/ + +//- setup +function decorator() { + return () => {}; +} +var _ = decorator; +var \u{6F} = decorator; +var \u2118 = decorator; +var ZW_\u200C_NJ = decorator; +var ZW_\u200D_J = decorator; +var yield = decorator; +var await = decorator; + +//- decorators +@$() +@_() +@\u{6F}() +@\u2118() +@ZW_\u200C_NJ() +@ZW_\u200D_J() +@yield() +@await() diff --git a/src/decorator/decorator-member-expr-decorator-member-expr.case b/src/decorator/decorator-member-expr-decorator-member-expr.case new file mode 100644 index 0000000000..be5fd8ed68 --- /dev/null +++ b/src/decorator/decorator-member-expr-decorator-member-expr.case @@ -0,0 +1,36 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +desc: > + Decorator @ DecoratorMemberExpression +info: | + DecoratorMemberExpression[Yield, Await] : + IdentifierReference[?Yield, ?Await] + PrivateIdentifier + DecoratorMemberExpression[?Yield, ?Await] . IdentifierName + +template: syntax/valid +---*/ + +//- setup +let ns = { + $() {} + _() {} + \u{6F}() {} + \u2118() {} + ZW_\u200C_NJ() {} + ZW_\u200D_J() {} + yield() {} + await() {} +} + +//- decorators +@ns.$ +@ns._ +@ns.\u{6F} +@ns.\u2118 +@ns.ZW_\u200C_NJ +@ns.ZW_\u200D_J +@ns.yield +@ns.await diff --git a/src/decorator/decorator-member-expr-identifier-reference.case b/src/decorator/decorator-member-expr-identifier-reference.case new file mode 100644 index 0000000000..16d5d97002 --- /dev/null +++ b/src/decorator/decorator-member-expr-identifier-reference.case @@ -0,0 +1,33 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +desc: > + Decorator @ DecoratorMemberExpression +info: | + IdentifierReference[Yield, Await] : + Identifier + [~Yield] yield + [~Await] await +template: syntax/valid +---*/ + +//- setup +function $() {} +function _() {} +function \u{6F}() {} +function \u2118() {} +function ZW_\u200C_NJ() {} +function ZW_\u200D_J() {} +function yield() {} +function await() {} + +//- decorators +@$ +@_ +@\u{6F} +@\u2118 +@ZW_\u200C_NJ +@ZW_\u200D_J +@yield +@await diff --git a/src/decorator/decorator-member-expr-private-identifier.case b/src/decorator/decorator-member-expr-private-identifier.case new file mode 100644 index 0000000000..2fa51c0510 --- /dev/null +++ b/src/decorator/decorator-member-expr-private-identifier.case @@ -0,0 +1,35 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +desc: > + Decorator @ DecoratorMemberExpression +info: | + DecoratorMemberExpression[Yield, Await] : + PrivateIdentifier + + PrivateIdentifier :: + # IdentifierName + +template: syntax/class-valid +---*/ + +//- elements +static #$() {} +static #_() {} +static #\u{6F}() {} +static #\u2118() {} +static #ZW_\u200C_NJ() {} +static #ZW_\u200D_J() {} +static #yield() {} +static #await() {} + +//- decorators +@#$ +@#_ +@#\u{6F} +@#\u2118 +@#ZW_\u200C_NJ +@#ZW_\u200D_J +@#yield +@#await diff --git a/src/decorator/decorator-parenthesized-expr-identifier-reference.case b/src/decorator/decorator-parenthesized-expr-identifier-reference.case new file mode 100644 index 0000000000..4e192eff23 --- /dev/null +++ b/src/decorator/decorator-parenthesized-expr-identifier-reference.case @@ -0,0 +1,47 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +desc: > + Decorator @ DecoratorParenthesizedExpression +info: | + DecoratorParenthesizedExpression[Yield, Await] : + ( Expression[+In, ?Yield, ?Await] ) + + PrimaryExpression[Yield, Await] : + this + IdentifierReference[?Yield, ?Await] + Literal + ArrayLiteral[?Yield, ?Await] + ObjectLiteral[?Yield, ?Await] + FunctionExpression + ClassExpression[?Yield, ?Await] + GeneratorExpression + AsyncFunctionExpression + AsyncGeneratorExpression + RegularExpressionLiteral + TemplateLiteral[?Yield, ?Await, ~Tagged] + CoverParenthesizedExpressionAndArrowParameterList[?Yield, ?Await] + +template: syntax/valid +---*/ + +//- setup +function $() {} +function _() {} +function \u{6F}() {} +function \u2118() {} +function ZW_\u200C_NJ() {} +function ZW_\u200D_J() {} +function yield() {} +function await() {} + +//- decorators +@($) +@(_) +@(\u{6F}) +@(\u2118) +@(ZW_\u200C_NJ) +@(ZW_\u200D_J) +@(yield) +@(await) diff --git a/src/decorator/syntax/class-valid/cls-decl-decorators-valid-syntax.template b/src/decorator/syntax/class-valid/cls-decl-decorators-valid-syntax.template new file mode 100644 index 0000000000..9155bb8d38 --- /dev/null +++ b/src/decorator/syntax/class-valid/cls-decl-decorators-valid-syntax.template @@ -0,0 +1,30 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +esid: prod-ClassDeclaration +name: Valid syntax for decorator on class declaration in class body. +path: language/statements/class/decorator/syntax/class-valid/ +info: | + ClassDeclaration[Yield, Await, Default] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await] ClassTail[?Yield, ?Await] + [+Default] DecoratorList[?Yield, ?Await]opt class ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... +features: [class, decorators] +---*/ + +class C { + /*{ elements }*/ + static { + /*{ decorators }*/ class C {} + } +} diff --git a/src/decorator/syntax/class-valid/cls-expr-decorators-valid-syntax.template b/src/decorator/syntax/class-valid/cls-expr-decorators-valid-syntax.template new file mode 100644 index 0000000000..2d422003bb --- /dev/null +++ b/src/decorator/syntax/class-valid/cls-expr-decorators-valid-syntax.template @@ -0,0 +1,29 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +esid: prod-ClassExpression +name: Valid syntax for decorator on class expression in class body. +path: language/expressions/class/decorator/syntax/class-valid/ +info: | + ClassExpression[Yield, Await] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await]opt ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... +features: [class, decorators] +---*/ + +var C = class { + /*{ elements }*/ + static { + var C = /*{ decorators }*/ class {} + } +}; diff --git a/src/decorator/syntax/valid/cls-decl-decorators-valid-syntax.template b/src/decorator/syntax/valid/cls-decl-decorators-valid-syntax.template new file mode 100644 index 0000000000..e3f78608e3 --- /dev/null +++ b/src/decorator/syntax/valid/cls-decl-decorators-valid-syntax.template @@ -0,0 +1,25 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +esid: prod-ClassDeclaration +name: Valid syntax for decorator on class. +path: language/statements/class/decorator/syntax/valid/ +info: | + ClassDeclaration[Yield, Await, Default] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await] ClassTail[?Yield, ?Await] + [+Default] DecoratorList[?Yield, ?Await]opt class ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... +features: [class, decorators] +---*/ + +/*{ decorators }*/ class C {} diff --git a/src/decorator/syntax/valid/cls-element-decorators-valid-syntax.template b/src/decorator/syntax/valid/cls-element-decorators-valid-syntax.template new file mode 100644 index 0000000000..6364cb8bcf --- /dev/null +++ b/src/decorator/syntax/valid/cls-element-decorators-valid-syntax.template @@ -0,0 +1,34 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +esid: prod-ClassDeclaration +name: Valid syntax for decorator on class. +path: language/statements/class/decorator/syntax/valid/ +info: | + ClassElement[Yield, Await] : + DecoratorList[?Yield, ?Await]opt MethodDefinition[?Yield, ?Await] + DecoratorList[?Yield, ?Await]opt static MethodDefinition[?Yield, ?Await] + DecoratorList[?Yield, ?Await]opt FieldDefinition[?Yield, ?Await] ; + DecoratorList[?Yield, ?Await]opt static FieldDefinition[?Yield, ?Await] ; + ClassStaticBlock + ; + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... +features: [class, decorators] +---*/ + +class C { + /*{ decorators }*/ method() {} + /*{ decorators }*/ static method() {} + /*{ decorators }*/ field; + /*{ decorators }*/ static field; +} diff --git a/src/decorator/syntax/valid/cls-expr-decorators-valid-syntax.template b/src/decorator/syntax/valid/cls-expr-decorators-valid-syntax.template new file mode 100644 index 0000000000..c71f04e1a9 --- /dev/null +++ b/src/decorator/syntax/valid/cls-expr-decorators-valid-syntax.template @@ -0,0 +1,24 @@ +// Copyright (C) 2022 Chengzhong Wu. All rights reserved. +// This code is governed by the BSD license found in the LICENSE file. + +/*--- +esid: prod-ClassExpression +name: Valid syntax for decorator on class expression +path: language/expressions/class/decorator/syntax/valid/ +info: | + ClassExpression[Yield, Await] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await]opt ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... +features: [class, decorators] +---*/ + +var C = /*{ decorators }*/ class {}; diff --git a/test/language/expressions/class/decorator/syntax/class-valid/decorator-member-expr-private-identifier.js b/test/language/expressions/class/decorator/syntax/class-valid/decorator-member-expr-private-identifier.js new file mode 100644 index 0000000000..a20d81200a --- /dev/null +++ b/test/language/expressions/class/decorator/syntax/class-valid/decorator-member-expr-private-identifier.js @@ -0,0 +1,53 @@ +// This file was procedurally generated from the following sources: +// - src/decorator/decorator-member-expr-private-identifier.case +// - src/decorator/syntax/class-valid/cls-expr-decorators-valid-syntax.template +/*--- +description: Decorator @ DecoratorMemberExpression (Valid syntax for decorator on class expression in class body.) +esid: prod-ClassExpression +features: [class, decorators] +flags: [generated] +info: | + ClassExpression[Yield, Await] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await]opt ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... + + + DecoratorMemberExpression[Yield, Await] : + PrivateIdentifier + + PrivateIdentifier :: + # IdentifierName + +---*/ + + +var C = class { + static #$() {} + static #_() {} + static #\u{6F}() {} + static #\u2118() {} + static #ZW_\u200C_NJ() {} + static #ZW_\u200D_J() {} + static #yield() {} + static #await() {} + + static { + var C = @#$ + @#_ + @#\u{6F} + @#\u2118 + @#ZW_\u200C_NJ + @#ZW_\u200D_J + @#yield + @#await class {} + } +}; diff --git a/test/language/expressions/class/decorator/syntax/valid/decorator-call-expr-identifier-reference.js b/test/language/expressions/class/decorator/syntax/valid/decorator-call-expr-identifier-reference.js new file mode 100644 index 0000000000..28bb48d799 --- /dev/null +++ b/test/language/expressions/class/decorator/syntax/valid/decorator-call-expr-identifier-reference.js @@ -0,0 +1,58 @@ +// This file was procedurally generated from the following sources: +// - src/decorator/decorator-call-expr-identifier-reference.case +// - src/decorator/syntax/valid/cls-expr-decorators-valid-syntax.template +/*--- +description: Decorator @ DecoratorCallExpression (Valid syntax for decorator on class expression) +esid: prod-ClassExpression +features: [class, decorators] +flags: [generated] +info: | + ClassExpression[Yield, Await] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await]opt ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... + + + DecoratorCallExpression[Yield, Await] : + DecoratorMemberExpression[?Yield, ?Await] Arguments[?Yield, ?Await] + + DecoratorMemberExpression[Yield, Await] : + IdentifierReference[?Yield, ?Await] + PrivateIdentifier + DecoratorMemberExpression[?Yield, ?Await] . IdentifierName + + IdentifierReference[Yield, Await] : + Identifier + [~Yield] yield + [~Await] await + +---*/ +function decorator() { + return () => {}; +} +var _ = decorator; +var \u{6F} = decorator; +var \u2118 = decorator; +var ZW_\u200C_NJ = decorator; +var ZW_\u200D_J = decorator; +var yield = decorator; +var await = decorator; + + + +var C = @$() +@_() +@\u{6F}() +@\u2118() +@ZW_\u200C_NJ() +@ZW_\u200D_J() +@yield() +@await() class {}; diff --git a/test/language/expressions/class/decorator/syntax/valid/decorator-member-expr-decorator-member-expr.js b/test/language/expressions/class/decorator/syntax/valid/decorator-member-expr-decorator-member-expr.js new file mode 100644 index 0000000000..ebbabb6f0c --- /dev/null +++ b/test/language/expressions/class/decorator/syntax/valid/decorator-member-expr-decorator-member-expr.js @@ -0,0 +1,50 @@ +// This file was procedurally generated from the following sources: +// - src/decorator/decorator-member-expr-decorator-member-expr.case +// - src/decorator/syntax/valid/cls-expr-decorators-valid-syntax.template +/*--- +description: Decorator @ DecoratorMemberExpression (Valid syntax for decorator on class expression) +esid: prod-ClassExpression +features: [class, decorators] +flags: [generated] +info: | + ClassExpression[Yield, Await] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await]opt ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... + + + DecoratorMemberExpression[Yield, Await] : + IdentifierReference[?Yield, ?Await] + PrivateIdentifier + DecoratorMemberExpression[?Yield, ?Await] . IdentifierName + +---*/ +let ns = { + $() {} + _() {} + \u{6F}() {} + \u2118() {} + ZW_\u200C_NJ() {} + ZW_\u200D_J() {} + yield() {} + await() {} +} + + + +var C = @ns.$ +@ns._ +@ns.\u{6F} +@ns.\u2118 +@ns.ZW_\u200C_NJ +@ns.ZW_\u200D_J +@ns.yield +@ns.await class {}; diff --git a/test/language/expressions/class/decorator/syntax/valid/decorator-member-expr-identifier-reference.js b/test/language/expressions/class/decorator/syntax/valid/decorator-member-expr-identifier-reference.js new file mode 100644 index 0000000000..18784fc2a8 --- /dev/null +++ b/test/language/expressions/class/decorator/syntax/valid/decorator-member-expr-identifier-reference.js @@ -0,0 +1,48 @@ +// This file was procedurally generated from the following sources: +// - src/decorator/decorator-member-expr-identifier-reference.case +// - src/decorator/syntax/valid/cls-expr-decorators-valid-syntax.template +/*--- +description: Decorator @ DecoratorMemberExpression (Valid syntax for decorator on class expression) +esid: prod-ClassExpression +features: [class, decorators] +flags: [generated] +info: | + ClassExpression[Yield, Await] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await]opt ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... + + + IdentifierReference[Yield, Await] : + Identifier + [~Yield] yield + [~Await] await + +---*/ +function $() {} +function _() {} +function \u{6F}() {} +function \u2118() {} +function ZW_\u200C_NJ() {} +function ZW_\u200D_J() {} +function yield() {} +function await() {} + + + +var C = @$ +@_ +@\u{6F} +@\u2118 +@ZW_\u200C_NJ +@ZW_\u200D_J +@yield +@await class {}; diff --git a/test/language/expressions/class/decorator/syntax/valid/decorator-parenthesized-expr-identifier-reference.js b/test/language/expressions/class/decorator/syntax/valid/decorator-parenthesized-expr-identifier-reference.js new file mode 100644 index 0000000000..d45939d0e4 --- /dev/null +++ b/test/language/expressions/class/decorator/syntax/valid/decorator-parenthesized-expr-identifier-reference.js @@ -0,0 +1,61 @@ +// This file was procedurally generated from the following sources: +// - src/decorator/decorator-parenthesized-expr-identifier-reference.case +// - src/decorator/syntax/valid/cls-expr-decorators-valid-syntax.template +/*--- +description: Decorator @ DecoratorParenthesizedExpression (Valid syntax for decorator on class expression) +esid: prod-ClassExpression +features: [class, decorators] +flags: [generated] +info: | + ClassExpression[Yield, Await] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await]opt ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... + + + DecoratorParenthesizedExpression[Yield, Await] : + ( Expression[+In, ?Yield, ?Await] ) + + PrimaryExpression[Yield, Await] : + this + IdentifierReference[?Yield, ?Await] + Literal + ArrayLiteral[?Yield, ?Await] + ObjectLiteral[?Yield, ?Await] + FunctionExpression + ClassExpression[?Yield, ?Await] + GeneratorExpression + AsyncFunctionExpression + AsyncGeneratorExpression + RegularExpressionLiteral + TemplateLiteral[?Yield, ?Await, ~Tagged] + CoverParenthesizedExpressionAndArrowParameterList[?Yield, ?Await] + +---*/ +function $() {} +function _() {} +function \u{6F}() {} +function \u2118() {} +function ZW_\u200C_NJ() {} +function ZW_\u200D_J() {} +function yield() {} +function await() {} + + + +var C = @($) +@(_) +@(\u{6F}) +@(\u2118) +@(ZW_\u200C_NJ) +@(ZW_\u200D_J) +@(yield) +@(await) class {}; diff --git a/test/language/expressions/class/elements/field-definition-accessor-no-line-terminator.js b/test/language/expressions/class/elements/field-definition-accessor-no-line-terminator.js new file mode 100644 index 0000000000..02a0068aed --- /dev/null +++ b/test/language/expressions/class/elements/field-definition-accessor-no-line-terminator.js @@ -0,0 +1,31 @@ +// This file was procedurally generated from the following sources: +// - src/class-elements/field-definition-accessor-no-line-terminator.case +// - src/class-elements/default/cls-expr.template +/*--- +description: Valid accessor FieldDefinition, ClassElementName, PropertyName Syntax (field definitions in a class expression) +esid: prod-FieldDefinition +features: [decorators, class] +flags: [generated] +info: | + FieldDefinition[Yield, Await] : + accessor [no LineTerminator here] ClassElementName[?Yield, ?Await] Initializer[+In, ?Yield, ?Await]opt + +---*/ + + +var C = class { + accessor + $; + static accessor + $; + +} + +let c = new C(); + +assert.sameValue(Object.hasOwnProperty.call(C.prototype, 'accessor'), false); +assert.sameValue(Object.hasOwnProperty.call(C.prototype, '$'), false); +assert.sameValue(Object.hasOwnProperty.call(C, 'accessor'), true); +assert.sameValue(Object.hasOwnProperty.call(C, '$'), true); +assert.sameValue(Object.hasOwnProperty.call(c, 'accessor'), true); +assert.sameValue(Object.hasOwnProperty.call(c, '$'), true); diff --git a/test/language/expressions/class/elements/syntax/valid/grammar-field-accessor.js b/test/language/expressions/class/elements/syntax/valid/grammar-field-accessor.js new file mode 100644 index 0000000000..d67fd328f6 --- /dev/null +++ b/test/language/expressions/class/elements/syntax/valid/grammar-field-accessor.js @@ -0,0 +1,24 @@ +// This file was procedurally generated from the following sources: +// - src/class-elements/grammar-field-accessor.case +// - src/class-elements/syntax/valid/cls-expr-elements-valid-syntax.template +/*--- +description: Valid accessor FieldDefinition, ClassElementName, PropertyName Syntax (class expression) +esid: prod-ClassElement +features: [decorators, class] +flags: [generated] +info: | + FieldDefinition[Yield, Await] : + ClassElementName[?Yield, ?Await] Initializer[+In, ?Yield, ?Await]opt + accessor [no LineTerminator here] ClassElementName[?Yield, ?Await] Initializer[+In, ?Yield, ?Await]opt + +---*/ + + +var C = class { + accessor $; + accessor _; + accessor \u{6F}; + accessor \u2118; + accessor ZW_\u200C_NJ; + accessor ZW_\u200D_J; +}; diff --git a/test/language/statements/class/decorator/syntax/class-valid/decorator-member-expr-private-identifier.js b/test/language/statements/class/decorator/syntax/class-valid/decorator-member-expr-private-identifier.js new file mode 100644 index 0000000000..24af7d9e5c --- /dev/null +++ b/test/language/statements/class/decorator/syntax/class-valid/decorator-member-expr-private-identifier.js @@ -0,0 +1,54 @@ +// This file was procedurally generated from the following sources: +// - src/decorator/decorator-member-expr-private-identifier.case +// - src/decorator/syntax/class-valid/cls-decl-decorators-valid-syntax.template +/*--- +description: Decorator @ DecoratorMemberExpression (Valid syntax for decorator on class declaration in class body.) +esid: prod-ClassDeclaration +features: [class, decorators] +flags: [generated] +info: | + ClassDeclaration[Yield, Await, Default] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await] ClassTail[?Yield, ?Await] + [+Default] DecoratorList[?Yield, ?Await]opt class ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... + + + DecoratorMemberExpression[Yield, Await] : + PrivateIdentifier + + PrivateIdentifier :: + # IdentifierName + +---*/ + + +class C { + static #$() {} + static #_() {} + static #\u{6F}() {} + static #\u2118() {} + static #ZW_\u200C_NJ() {} + static #ZW_\u200D_J() {} + static #yield() {} + static #await() {} + + static { + @#$ + @#_ + @#\u{6F} + @#\u2118 + @#ZW_\u200C_NJ + @#ZW_\u200D_J + @#yield + @#await class C {} + } +} diff --git a/test/language/statements/class/decorator/syntax/valid/decorator-call-expr-identifier-reference.js b/test/language/statements/class/decorator/syntax/valid/decorator-call-expr-identifier-reference.js new file mode 100644 index 0000000000..4a086df498 --- /dev/null +++ b/test/language/statements/class/decorator/syntax/valid/decorator-call-expr-identifier-reference.js @@ -0,0 +1,59 @@ +// This file was procedurally generated from the following sources: +// - src/decorator/decorator-call-expr-identifier-reference.case +// - src/decorator/syntax/valid/cls-decl-decorators-valid-syntax.template +/*--- +description: Decorator @ DecoratorCallExpression (Valid syntax for decorator on class.) +esid: prod-ClassDeclaration +features: [class, decorators] +flags: [generated] +info: | + ClassDeclaration[Yield, Await, Default] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await] ClassTail[?Yield, ?Await] + [+Default] DecoratorList[?Yield, ?Await]opt class ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... + + + DecoratorCallExpression[Yield, Await] : + DecoratorMemberExpression[?Yield, ?Await] Arguments[?Yield, ?Await] + + DecoratorMemberExpression[Yield, Await] : + IdentifierReference[?Yield, ?Await] + PrivateIdentifier + DecoratorMemberExpression[?Yield, ?Await] . IdentifierName + + IdentifierReference[Yield, Await] : + Identifier + [~Yield] yield + [~Await] await + +---*/ +function decorator() { + return () => {}; +} +var _ = decorator; +var \u{6F} = decorator; +var \u2118 = decorator; +var ZW_\u200C_NJ = decorator; +var ZW_\u200D_J = decorator; +var yield = decorator; +var await = decorator; + + + +@$() +@_() +@\u{6F}() +@\u2118() +@ZW_\u200C_NJ() +@ZW_\u200D_J() +@yield() +@await() class C {} diff --git a/test/language/statements/class/decorator/syntax/valid/decorator-member-expr-decorator-member-expr.js b/test/language/statements/class/decorator/syntax/valid/decorator-member-expr-decorator-member-expr.js new file mode 100644 index 0000000000..f13312ce55 --- /dev/null +++ b/test/language/statements/class/decorator/syntax/valid/decorator-member-expr-decorator-member-expr.js @@ -0,0 +1,51 @@ +// This file was procedurally generated from the following sources: +// - src/decorator/decorator-member-expr-decorator-member-expr.case +// - src/decorator/syntax/valid/cls-decl-decorators-valid-syntax.template +/*--- +description: Decorator @ DecoratorMemberExpression (Valid syntax for decorator on class.) +esid: prod-ClassDeclaration +features: [class, decorators] +flags: [generated] +info: | + ClassDeclaration[Yield, Await, Default] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await] ClassTail[?Yield, ?Await] + [+Default] DecoratorList[?Yield, ?Await]opt class ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... + + + DecoratorMemberExpression[Yield, Await] : + IdentifierReference[?Yield, ?Await] + PrivateIdentifier + DecoratorMemberExpression[?Yield, ?Await] . IdentifierName + +---*/ +let ns = { + $() {} + _() {} + \u{6F}() {} + \u2118() {} + ZW_\u200C_NJ() {} + ZW_\u200D_J() {} + yield() {} + await() {} +} + + + +@ns.$ +@ns._ +@ns.\u{6F} +@ns.\u2118 +@ns.ZW_\u200C_NJ +@ns.ZW_\u200D_J +@ns.yield +@ns.await class C {} diff --git a/test/language/statements/class/decorator/syntax/valid/decorator-member-expr-identifier-reference.js b/test/language/statements/class/decorator/syntax/valid/decorator-member-expr-identifier-reference.js new file mode 100644 index 0000000000..eeabd1013a --- /dev/null +++ b/test/language/statements/class/decorator/syntax/valid/decorator-member-expr-identifier-reference.js @@ -0,0 +1,49 @@ +// This file was procedurally generated from the following sources: +// - src/decorator/decorator-member-expr-identifier-reference.case +// - src/decorator/syntax/valid/cls-decl-decorators-valid-syntax.template +/*--- +description: Decorator @ DecoratorMemberExpression (Valid syntax for decorator on class.) +esid: prod-ClassDeclaration +features: [class, decorators] +flags: [generated] +info: | + ClassDeclaration[Yield, Await, Default] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await] ClassTail[?Yield, ?Await] + [+Default] DecoratorList[?Yield, ?Await]opt class ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... + + + IdentifierReference[Yield, Await] : + Identifier + [~Yield] yield + [~Await] await + +---*/ +function $() {} +function _() {} +function \u{6F}() {} +function \u2118() {} +function ZW_\u200C_NJ() {} +function ZW_\u200D_J() {} +function yield() {} +function await() {} + + + +@$ +@_ +@\u{6F} +@\u2118 +@ZW_\u200C_NJ +@ZW_\u200D_J +@yield +@await class C {} diff --git a/test/language/statements/class/decorator/syntax/valid/decorator-parenthesized-expr-identifier-reference.js b/test/language/statements/class/decorator/syntax/valid/decorator-parenthesized-expr-identifier-reference.js new file mode 100644 index 0000000000..9d55b8233a --- /dev/null +++ b/test/language/statements/class/decorator/syntax/valid/decorator-parenthesized-expr-identifier-reference.js @@ -0,0 +1,62 @@ +// This file was procedurally generated from the following sources: +// - src/decorator/decorator-parenthesized-expr-identifier-reference.case +// - src/decorator/syntax/valid/cls-decl-decorators-valid-syntax.template +/*--- +description: Decorator @ DecoratorParenthesizedExpression (Valid syntax for decorator on class.) +esid: prod-ClassDeclaration +features: [class, decorators] +flags: [generated] +info: | + ClassDeclaration[Yield, Await, Default] : + DecoratorList[?Yield, ?Await]opt class BindingIdentifier[?Yield, ?Await] ClassTail[?Yield, ?Await] + [+Default] DecoratorList[?Yield, ?Await]opt class ClassTail[?Yield, ?Await] + + DecoratorList[Yield, Await] : + DecoratorList[?Yield, ?Await]opt Decorator[?Yield, ?Await] + + Decorator[Yield, Await] : + @ DecoratorMemberExpression[?Yield, ?Await] + @ DecoratorParenthesizedExpression[?Yield, ?Await] + @ DecoratorCallExpression[?Yield, ?Await] + + ... + + + DecoratorParenthesizedExpression[Yield, Await] : + ( Expression[+In, ?Yield, ?Await] ) + + PrimaryExpression[Yield, Await] : + this + IdentifierReference[?Yield, ?Await] + Literal + ArrayLiteral[?Yield, ?Await] + ObjectLiteral[?Yield, ?Await] + FunctionExpression + ClassExpression[?Yield, ?Await] + GeneratorExpression + AsyncFunctionExpression + AsyncGeneratorExpression + RegularExpressionLiteral + TemplateLiteral[?Yield, ?Await, ~Tagged] + CoverParenthesizedExpressionAndArrowParameterList[?Yield, ?Await] + +---*/ +function $() {} +function _() {} +function \u{6F}() {} +function \u2118() {} +function ZW_\u200C_NJ() {} +function ZW_\u200D_J() {} +function yield() {} +function await() {} + + + +@($) +@(_) +@(\u{6F}) +@(\u2118) +@(ZW_\u200C_NJ) +@(ZW_\u200D_J) +@(yield) +@(await) class C {} diff --git a/test/language/statements/class/elements/field-definition-accessor-no-line-terminator.js b/test/language/statements/class/elements/field-definition-accessor-no-line-terminator.js new file mode 100644 index 0000000000..f09f713a4b --- /dev/null +++ b/test/language/statements/class/elements/field-definition-accessor-no-line-terminator.js @@ -0,0 +1,31 @@ +// This file was procedurally generated from the following sources: +// - src/class-elements/field-definition-accessor-no-line-terminator.case +// - src/class-elements/default/cls-decl.template +/*--- +description: Valid accessor FieldDefinition, ClassElementName, PropertyName Syntax (field definitions in a class declaration) +esid: prod-FieldDefinition +features: [decorators, class] +flags: [generated] +info: | + FieldDefinition[Yield, Await] : + accessor [no LineTerminator here] ClassElementName[?Yield, ?Await] Initializer[+In, ?Yield, ?Await]opt + +---*/ + + +class C { + accessor + $; + static accessor + $; + +} + +let c = new C(); + +assert.sameValue(Object.hasOwnProperty.call(C.prototype, 'accessor'), false); +assert.sameValue(Object.hasOwnProperty.call(C.prototype, '$'), false); +assert.sameValue(Object.hasOwnProperty.call(C, 'accessor'), true); +assert.sameValue(Object.hasOwnProperty.call(C, '$'), true); +assert.sameValue(Object.hasOwnProperty.call(c, 'accessor'), true); +assert.sameValue(Object.hasOwnProperty.call(c, '$'), true); diff --git a/test/language/statements/class/elements/syntax/valid/grammar-field-accessor.js b/test/language/statements/class/elements/syntax/valid/grammar-field-accessor.js new file mode 100644 index 0000000000..9091ed8a95 --- /dev/null +++ b/test/language/statements/class/elements/syntax/valid/grammar-field-accessor.js @@ -0,0 +1,24 @@ +// This file was procedurally generated from the following sources: +// - src/class-elements/grammar-field-accessor.case +// - src/class-elements/syntax/valid/cls-decl-elements-valid-syntax.template +/*--- +description: Valid accessor FieldDefinition, ClassElementName, PropertyName Syntax (class declaration) +esid: prod-ClassElement +features: [decorators, class] +flags: [generated] +info: | + FieldDefinition[Yield, Await] : + ClassElementName[?Yield, ?Await] Initializer[+In, ?Yield, ?Await]opt + accessor [no LineTerminator here] ClassElementName[?Yield, ?Await] Initializer[+In, ?Yield, ?Await]opt + +---*/ + + +class C { + accessor $; + accessor _; + accessor \u{6F}; + accessor \u2118; + accessor ZW_\u200C_NJ; + accessor ZW_\u200D_J; +}