From 35a60af4a757aa841b6f7ce1d8eb0b07009d678e Mon Sep 17 00:00:00 2001 From: Denis Bezrukov <6227442+denbezrukov@users.noreply.github.com> Date: Sun, 30 Apr 2023 15:40:00 +0300 Subject: [PATCH] feat(rome_js_parser): EcmaScript @decorators #4252 --- crates/rome_js_parser/src/syntax/class.rs | 28 +- crates/rome_js_parser/src/syntax/function.rs | 11 +- .../inline/err/decorator_parameters.rast | 132 -------- .../err/ts_formal_parameter_decorator.rast | 287 ------------------ .../ok/decorator_parameters_constructor.rast | 93 ++++++ .../decorator_parameters_constructor.ts} | 0 .../ok/ts_formal_parameter_decorator.rast | 193 ++++++++++++ .../ts_formal_parameter_decorator.ts | 0 8 files changed, 317 insertions(+), 427 deletions(-) delete mode 100644 crates/rome_js_parser/test_data/inline/err/decorator_parameters.rast delete mode 100644 crates/rome_js_parser/test_data/inline/err/ts_formal_parameter_decorator.rast create mode 100644 crates/rome_js_parser/test_data/inline/ok/decorator_parameters_constructor.rast rename crates/rome_js_parser/test_data/inline/{err/decorator_parameters.ts => ok/decorator_parameters_constructor.ts} (100%) create mode 100644 crates/rome_js_parser/test_data/inline/ok/ts_formal_parameter_decorator.rast rename crates/rome_js_parser/test_data/inline/{err => ok}/ts_formal_parameter_decorator.ts (100%) diff --git a/crates/rome_js_parser/src/syntax/class.rs b/crates/rome_js_parser/src/syntax/class.rs index c973c6c6306..8e9f121fd01 100644 --- a/crates/rome_js_parser/src/syntax/class.rs +++ b/crates/rome_js_parser/src/syntax/class.rs @@ -2156,7 +2156,7 @@ impl ClassMemberModifiers { | JS_SETTER_CLASS_MEMBER ) { - // test_err ts decorator_parameters + // test ts decorator_parameters_constructor // class Foo { // constructor(@dec a: string) {} // } @@ -2642,3 +2642,29 @@ fn parse_decorator(p: &mut JsParser) -> ParsedSyntax { Present(m.complete(p, JS_DECORATOR)) } + +/// Skips over any TypeScript decorator syntax. +pub(crate) fn skip_ts_decorators(p: &mut JsParser) { + if !p.at(T![@]) { + return; + } + + p.parse_as_skipped_trivia_tokens(|p| { + while p.at(T![@]) { + parse_decorator_bogus(p).ok(); + } + }); +} + +fn parse_decorator_bogus(p: &mut JsParser) -> ParsedSyntax { + if p.at(T![@]) { + let m = p.start(); + p.bump(T![@]); + parse_lhs_expr(p, ExpressionContext::default().and_in_decorator(true)) + .or_add_diagnostic(p, expected_expression); + + Present(m.complete(p, JS_BOGUS)) + } else { + Absent + } +} diff --git a/crates/rome_js_parser/src/syntax/function.rs b/crates/rome_js_parser/src/syntax/function.rs index 15b55644a7b..30b9afaff93 100644 --- a/crates/rome_js_parser/src/syntax/function.rs +++ b/crates/rome_js_parser/src/syntax/function.rs @@ -4,14 +4,12 @@ use crate::state::{EnterFunction, EnterParameters, SignatureFlags}; use crate::syntax::binding::{ is_at_identifier_binding, is_nth_at_identifier_binding, parse_binding, parse_binding_pattern, }; -use crate::syntax::class::{parse_decorators, parse_initializer_clause}; +use crate::syntax::class::{parse_initializer_clause, skip_ts_decorators}; use crate::syntax::expr::{ is_nth_at_identifier, parse_assignment_expression_or_higher, ExpressionContext, }; use crate::syntax::js_parse_error; -use crate::syntax::js_parse_error::{ - decorators_not_allowed, expected_binding, expected_parameter, expected_parameters, -}; +use crate::syntax::js_parse_error::{expected_binding, expected_parameter, expected_parameters}; use crate::syntax::stmt::{is_semi, parse_block_impl, semi, StatementContext}; use crate::syntax::typescript::ts_parse_error::ts_only_syntax_error; use crate::syntax::typescript::{ @@ -1026,14 +1024,13 @@ pub(crate) fn parse_formal_parameter( parameter_context: ParameterContext, expression_context: ExpressionContext, ) -> ParsedSyntax { - // test_err ts ts_formal_parameter_decorator + // test ts ts_formal_parameter_decorator // function a(@dec x) {} // class Foo { // constructor(@dec x) {} // method(@dec x) {} // } - let decorator_list = parse_decorators(p); - decorator_list.add_diagnostic_if_present(p, decorators_not_allowed); + skip_ts_decorators(p); parse_binding_pattern(p, expression_context).map(|binding| { let binding_kind = binding.kind(p); diff --git a/crates/rome_js_parser/test_data/inline/err/decorator_parameters.rast b/crates/rome_js_parser/test_data/inline/err/decorator_parameters.rast deleted file mode 100644 index f57f10a7dbd..00000000000 --- a/crates/rome_js_parser/test_data/inline/err/decorator_parameters.rast +++ /dev/null @@ -1,132 +0,0 @@ -JsModule { - interpreter_token: missing (optional), - directives: JsDirectiveList [], - items: JsModuleItemList [ - JsClassDeclaration { - decorators: JsDecoratorList [], - abstract_token: missing (optional), - class_token: CLASS_KW@0..6 "class" [] [Whitespace(" ")], - id: JsIdentifierBinding { - name_token: IDENT@6..10 "Foo" [] [Whitespace(" ")], - }, - type_parameters: missing (optional), - extends_clause: missing (optional), - implements_clause: missing (optional), - l_curly_token: L_CURLY@10..11 "{" [] [], - members: JsClassMemberList [ - JsBogusMember { - items: [ - JsConstructorModifierList [], - JsLiteralMemberName { - value: IDENT@11..26 "constructor" [Newline("\n"), Whitespace(" ")] [], - }, - JsBogus { - items: [ - L_PAREN@26..27 "(" [] [], - JsBogus { - items: [ - JsDecoratorList [ - JsDecorator { - at_token: AT@27..28 "@" [] [], - expression: JsIdentifierExpression { - name: JsReferenceIdentifier { - value_token: IDENT@28..32 "dec" [] [Whitespace(" ")], - }, - }, - }, - ], - JsFormalParameter { - binding: JsIdentifierBinding { - name_token: IDENT@32..33 "a" [] [], - }, - question_mark_token: missing (optional), - type_annotation: TsTypeAnnotation { - colon_token: COLON@33..35 ":" [] [Whitespace(" ")], - ty: TsStringType { - string_token: STRING_KW@35..41 "string" [] [], - }, - }, - initializer: missing (optional), - }, - ], - }, - R_PAREN@41..43 ")" [] [Whitespace(" ")], - ], - }, - JsFunctionBody { - l_curly_token: L_CURLY@43..44 "{" [] [], - directives: JsDirectiveList [], - statements: JsStatementList [], - r_curly_token: R_CURLY@44..45 "}" [] [], - }, - ], - }, - ], - r_curly_token: R_CURLY@45..47 "}" [Newline("\n")] [], - }, - ], - eof_token: EOF@47..48 "" [Newline("\n")] [], -} - -0: JS_MODULE@0..48 - 0: (empty) - 1: JS_DIRECTIVE_LIST@0..0 - 2: JS_MODULE_ITEM_LIST@0..47 - 0: JS_CLASS_DECLARATION@0..47 - 0: JS_DECORATOR_LIST@0..0 - 1: (empty) - 2: CLASS_KW@0..6 "class" [] [Whitespace(" ")] - 3: JS_IDENTIFIER_BINDING@6..10 - 0: IDENT@6..10 "Foo" [] [Whitespace(" ")] - 4: (empty) - 5: (empty) - 6: (empty) - 7: L_CURLY@10..11 "{" [] [] - 8: JS_CLASS_MEMBER_LIST@11..45 - 0: JS_BOGUS_MEMBER@11..45 - 0: JS_CONSTRUCTOR_MODIFIER_LIST@11..11 - 1: JS_LITERAL_MEMBER_NAME@11..26 - 0: IDENT@11..26 "constructor" [Newline("\n"), Whitespace(" ")] [] - 2: JS_BOGUS@26..43 - 0: L_PAREN@26..27 "(" [] [] - 1: JS_BOGUS@27..41 - 0: JS_DECORATOR_LIST@27..32 - 0: JS_DECORATOR@27..32 - 0: AT@27..28 "@" [] [] - 1: JS_IDENTIFIER_EXPRESSION@28..32 - 0: JS_REFERENCE_IDENTIFIER@28..32 - 0: IDENT@28..32 "dec" [] [Whitespace(" ")] - 1: JS_FORMAL_PARAMETER@32..41 - 0: JS_IDENTIFIER_BINDING@32..33 - 0: IDENT@32..33 "a" [] [] - 1: (empty) - 2: TS_TYPE_ANNOTATION@33..41 - 0: COLON@33..35 ":" [] [Whitespace(" ")] - 1: TS_STRING_TYPE@35..41 - 0: STRING_KW@35..41 "string" [] [] - 3: (empty) - 2: R_PAREN@41..43 ")" [] [Whitespace(" ")] - 3: JS_FUNCTION_BODY@43..45 - 0: L_CURLY@43..44 "{" [] [] - 1: JS_DIRECTIVE_LIST@44..44 - 2: JS_STATEMENT_LIST@44..44 - 3: R_CURLY@44..45 "}" [] [] - 9: R_CURLY@45..47 "}" [Newline("\n")] [] - 3: EOF@47..48 "" [Newline("\n")] [] --- -decorator_parameters.ts:2:16 parse ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ - - × Decorators are not valid here. - - 1 │ class Foo { - > 2 │ constructor(@dec a: string) {} - │ ^^^^ - 3 │ } - 4 │ - - i Decorators are only valid on class declarations, class expressions, and class methods. - --- -class Foo { - constructor(@dec a: string) {} -} diff --git a/crates/rome_js_parser/test_data/inline/err/ts_formal_parameter_decorator.rast b/crates/rome_js_parser/test_data/inline/err/ts_formal_parameter_decorator.rast deleted file mode 100644 index 3483f4507a8..00000000000 --- a/crates/rome_js_parser/test_data/inline/err/ts_formal_parameter_decorator.rast +++ /dev/null @@ -1,287 +0,0 @@ -JsModule { - interpreter_token: missing (optional), - directives: JsDirectiveList [], - items: JsModuleItemList [ - JsBogusStatement { - items: [ - FUNCTION_KW@0..9 "function" [] [Whitespace(" ")], - JsIdentifierBinding { - name_token: IDENT@9..10 "a" [] [], - }, - JsBogus { - items: [ - L_PAREN@10..11 "(" [] [], - JsBogus { - items: [ - JsDecoratorList [ - JsDecorator { - at_token: AT@11..12 "@" [] [], - expression: JsIdentifierExpression { - name: JsReferenceIdentifier { - value_token: IDENT@12..16 "dec" [] [Whitespace(" ")], - }, - }, - }, - ], - JsFormalParameter { - binding: JsIdentifierBinding { - name_token: IDENT@16..17 "x" [] [], - }, - question_mark_token: missing (optional), - type_annotation: missing (optional), - initializer: missing (optional), - }, - ], - }, - R_PAREN@17..19 ")" [] [Whitespace(" ")], - ], - }, - JsFunctionBody { - l_curly_token: L_CURLY@19..20 "{" [] [], - directives: JsDirectiveList [], - statements: JsStatementList [], - r_curly_token: R_CURLY@20..21 "}" [] [], - }, - ], - }, - JsClassDeclaration { - decorators: JsDecoratorList [], - abstract_token: missing (optional), - class_token: CLASS_KW@21..28 "class" [Newline("\n")] [Whitespace(" ")], - id: JsIdentifierBinding { - name_token: IDENT@28..32 "Foo" [] [Whitespace(" ")], - }, - type_parameters: missing (optional), - extends_clause: missing (optional), - implements_clause: missing (optional), - l_curly_token: L_CURLY@32..33 "{" [] [], - members: JsClassMemberList [ - JsBogusMember { - items: [ - JsConstructorModifierList [], - JsLiteralMemberName { - value: IDENT@33..48 "constructor" [Newline("\n"), Whitespace(" ")] [], - }, - JsBogus { - items: [ - L_PAREN@48..49 "(" [] [], - JsBogus { - items: [ - JsDecoratorList [ - JsDecorator { - at_token: AT@49..50 "@" [] [], - expression: JsIdentifierExpression { - name: JsReferenceIdentifier { - value_token: IDENT@50..54 "dec" [] [Whitespace(" ")], - }, - }, - }, - ], - JsFormalParameter { - binding: JsIdentifierBinding { - name_token: IDENT@54..55 "x" [] [], - }, - question_mark_token: missing (optional), - type_annotation: missing (optional), - initializer: missing (optional), - }, - ], - }, - R_PAREN@55..57 ")" [] [Whitespace(" ")], - ], - }, - JsFunctionBody { - l_curly_token: L_CURLY@57..58 "{" [] [], - directives: JsDirectiveList [], - statements: JsStatementList [], - r_curly_token: R_CURLY@58..59 "}" [] [], - }, - ], - }, - JsBogusMember { - items: [ - JsMethodModifierList [], - JsLiteralMemberName { - value: IDENT@59..69 "method" [Newline("\n"), Whitespace(" ")] [], - }, - JsBogus { - items: [ - L_PAREN@69..70 "(" [] [], - JsBogus { - items: [ - JsDecoratorList [ - JsDecorator { - at_token: AT@70..71 "@" [] [], - expression: JsIdentifierExpression { - name: JsReferenceIdentifier { - value_token: IDENT@71..75 "dec" [] [Whitespace(" ")], - }, - }, - }, - ], - JsFormalParameter { - binding: JsIdentifierBinding { - name_token: IDENT@75..76 "x" [] [], - }, - question_mark_token: missing (optional), - type_annotation: missing (optional), - initializer: missing (optional), - }, - ], - }, - R_PAREN@76..78 ")" [] [Whitespace(" ")], - ], - }, - JsFunctionBody { - l_curly_token: L_CURLY@78..79 "{" [] [], - directives: JsDirectiveList [], - statements: JsStatementList [], - r_curly_token: R_CURLY@79..80 "}" [] [], - }, - ], - }, - ], - r_curly_token: R_CURLY@80..82 "}" [Newline("\n")] [], - }, - ], - eof_token: EOF@82..83 "" [Newline("\n")] [], -} - -0: JS_MODULE@0..83 - 0: (empty) - 1: JS_DIRECTIVE_LIST@0..0 - 2: JS_MODULE_ITEM_LIST@0..82 - 0: JS_BOGUS_STATEMENT@0..21 - 0: FUNCTION_KW@0..9 "function" [] [Whitespace(" ")] - 1: JS_IDENTIFIER_BINDING@9..10 - 0: IDENT@9..10 "a" [] [] - 2: JS_BOGUS@10..19 - 0: L_PAREN@10..11 "(" [] [] - 1: JS_BOGUS@11..17 - 0: JS_DECORATOR_LIST@11..16 - 0: JS_DECORATOR@11..16 - 0: AT@11..12 "@" [] [] - 1: JS_IDENTIFIER_EXPRESSION@12..16 - 0: JS_REFERENCE_IDENTIFIER@12..16 - 0: IDENT@12..16 "dec" [] [Whitespace(" ")] - 1: JS_FORMAL_PARAMETER@16..17 - 0: JS_IDENTIFIER_BINDING@16..17 - 0: IDENT@16..17 "x" [] [] - 1: (empty) - 2: (empty) - 3: (empty) - 2: R_PAREN@17..19 ")" [] [Whitespace(" ")] - 3: JS_FUNCTION_BODY@19..21 - 0: L_CURLY@19..20 "{" [] [] - 1: JS_DIRECTIVE_LIST@20..20 - 2: JS_STATEMENT_LIST@20..20 - 3: R_CURLY@20..21 "}" [] [] - 1: JS_CLASS_DECLARATION@21..82 - 0: JS_DECORATOR_LIST@21..21 - 1: (empty) - 2: CLASS_KW@21..28 "class" [Newline("\n")] [Whitespace(" ")] - 3: JS_IDENTIFIER_BINDING@28..32 - 0: IDENT@28..32 "Foo" [] [Whitespace(" ")] - 4: (empty) - 5: (empty) - 6: (empty) - 7: L_CURLY@32..33 "{" [] [] - 8: JS_CLASS_MEMBER_LIST@33..80 - 0: JS_BOGUS_MEMBER@33..59 - 0: JS_CONSTRUCTOR_MODIFIER_LIST@33..33 - 1: JS_LITERAL_MEMBER_NAME@33..48 - 0: IDENT@33..48 "constructor" [Newline("\n"), Whitespace(" ")] [] - 2: JS_BOGUS@48..57 - 0: L_PAREN@48..49 "(" [] [] - 1: JS_BOGUS@49..55 - 0: JS_DECORATOR_LIST@49..54 - 0: JS_DECORATOR@49..54 - 0: AT@49..50 "@" [] [] - 1: JS_IDENTIFIER_EXPRESSION@50..54 - 0: JS_REFERENCE_IDENTIFIER@50..54 - 0: IDENT@50..54 "dec" [] [Whitespace(" ")] - 1: JS_FORMAL_PARAMETER@54..55 - 0: JS_IDENTIFIER_BINDING@54..55 - 0: IDENT@54..55 "x" [] [] - 1: (empty) - 2: (empty) - 3: (empty) - 2: R_PAREN@55..57 ")" [] [Whitespace(" ")] - 3: JS_FUNCTION_BODY@57..59 - 0: L_CURLY@57..58 "{" [] [] - 1: JS_DIRECTIVE_LIST@58..58 - 2: JS_STATEMENT_LIST@58..58 - 3: R_CURLY@58..59 "}" [] [] - 1: JS_BOGUS_MEMBER@59..80 - 0: JS_METHOD_MODIFIER_LIST@59..59 - 1: JS_LITERAL_MEMBER_NAME@59..69 - 0: IDENT@59..69 "method" [Newline("\n"), Whitespace(" ")] [] - 2: JS_BOGUS@69..78 - 0: L_PAREN@69..70 "(" [] [] - 1: JS_BOGUS@70..76 - 0: JS_DECORATOR_LIST@70..75 - 0: JS_DECORATOR@70..75 - 0: AT@70..71 "@" [] [] - 1: JS_IDENTIFIER_EXPRESSION@71..75 - 0: JS_REFERENCE_IDENTIFIER@71..75 - 0: IDENT@71..75 "dec" [] [Whitespace(" ")] - 1: JS_FORMAL_PARAMETER@75..76 - 0: JS_IDENTIFIER_BINDING@75..76 - 0: IDENT@75..76 "x" [] [] - 1: (empty) - 2: (empty) - 3: (empty) - 2: R_PAREN@76..78 ")" [] [Whitespace(" ")] - 3: JS_FUNCTION_BODY@78..80 - 0: L_CURLY@78..79 "{" [] [] - 1: JS_DIRECTIVE_LIST@79..79 - 2: JS_STATEMENT_LIST@79..79 - 3: R_CURLY@79..80 "}" [] [] - 9: R_CURLY@80..82 "}" [Newline("\n")] [] - 3: EOF@82..83 "" [Newline("\n")] [] --- -ts_formal_parameter_decorator.ts:1:12 parse ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ - - × Decorators are not valid here. - - > 1 │ function a(@dec x) {} - │ ^^^^ - 2 │ class Foo { - 3 │ constructor(@dec x) {} - - i Decorators are only valid on class declarations, class expressions, and class methods. - --- -ts_formal_parameter_decorator.ts:3:16 parse ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ - - × Decorators are not valid here. - - 1 │ function a(@dec x) {} - 2 │ class Foo { - > 3 │ constructor(@dec x) {} - │ ^^^^ - 4 │ method(@dec x) {} - 5 │ } - - i Decorators are only valid on class declarations, class expressions, and class methods. - --- -ts_formal_parameter_decorator.ts:4:11 parse ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ - - × Decorators are not valid here. - - 2 │ class Foo { - 3 │ constructor(@dec x) {} - > 4 │ method(@dec x) {} - │ ^^^^ - 5 │ } - 6 │ - - i Decorators are only valid on class declarations, class expressions, and class methods. - --- -function a(@dec x) {} -class Foo { - constructor(@dec x) {} - method(@dec x) {} -} diff --git a/crates/rome_js_parser/test_data/inline/ok/decorator_parameters_constructor.rast b/crates/rome_js_parser/test_data/inline/ok/decorator_parameters_constructor.rast new file mode 100644 index 00000000000..eaf05551b48 --- /dev/null +++ b/crates/rome_js_parser/test_data/inline/ok/decorator_parameters_constructor.rast @@ -0,0 +1,93 @@ +JsModule { + interpreter_token: missing (optional), + directives: JsDirectiveList [], + items: JsModuleItemList [ + JsClassDeclaration { + decorators: JsDecoratorList [], + abstract_token: missing (optional), + class_token: CLASS_KW@0..6 "class" [] [Whitespace(" ")], + id: JsIdentifierBinding { + name_token: IDENT@6..10 "Foo" [] [Whitespace(" ")], + }, + type_parameters: missing (optional), + extends_clause: missing (optional), + implements_clause: missing (optional), + l_curly_token: L_CURLY@10..11 "{" [] [], + members: JsClassMemberList [ + JsConstructorClassMember { + modifiers: JsConstructorModifierList [], + name: JsLiteralMemberName { + value: IDENT@11..26 "constructor" [Newline("\n"), Whitespace(" ")] [], + }, + parameters: JsConstructorParameters { + l_paren_token: L_PAREN@26..27 "(" [] [], + parameters: JsConstructorParameterList [ + JsFormalParameter { + binding: JsIdentifierBinding { + name_token: IDENT@27..33 "a" [Skipped("@"), Skipped("dec"), Whitespace(" ")] [], + }, + question_mark_token: missing (optional), + type_annotation: TsTypeAnnotation { + colon_token: COLON@33..35 ":" [] [Whitespace(" ")], + ty: TsStringType { + string_token: STRING_KW@35..41 "string" [] [], + }, + }, + initializer: missing (optional), + }, + ], + r_paren_token: R_PAREN@41..43 ")" [] [Whitespace(" ")], + }, + body: JsFunctionBody { + l_curly_token: L_CURLY@43..44 "{" [] [], + directives: JsDirectiveList [], + statements: JsStatementList [], + r_curly_token: R_CURLY@44..45 "}" [] [], + }, + }, + ], + r_curly_token: R_CURLY@45..47 "}" [Newline("\n")] [], + }, + ], + eof_token: EOF@47..48 "" [Newline("\n")] [], +} + +0: JS_MODULE@0..48 + 0: (empty) + 1: JS_DIRECTIVE_LIST@0..0 + 2: JS_MODULE_ITEM_LIST@0..47 + 0: JS_CLASS_DECLARATION@0..47 + 0: JS_DECORATOR_LIST@0..0 + 1: (empty) + 2: CLASS_KW@0..6 "class" [] [Whitespace(" ")] + 3: JS_IDENTIFIER_BINDING@6..10 + 0: IDENT@6..10 "Foo" [] [Whitespace(" ")] + 4: (empty) + 5: (empty) + 6: (empty) + 7: L_CURLY@10..11 "{" [] [] + 8: JS_CLASS_MEMBER_LIST@11..45 + 0: JS_CONSTRUCTOR_CLASS_MEMBER@11..45 + 0: JS_CONSTRUCTOR_MODIFIER_LIST@11..11 + 1: JS_LITERAL_MEMBER_NAME@11..26 + 0: IDENT@11..26 "constructor" [Newline("\n"), Whitespace(" ")] [] + 2: JS_CONSTRUCTOR_PARAMETERS@26..43 + 0: L_PAREN@26..27 "(" [] [] + 1: JS_CONSTRUCTOR_PARAMETER_LIST@27..41 + 0: JS_FORMAL_PARAMETER@27..41 + 0: JS_IDENTIFIER_BINDING@27..33 + 0: IDENT@27..33 "a" [Skipped("@"), Skipped("dec"), Whitespace(" ")] [] + 1: (empty) + 2: TS_TYPE_ANNOTATION@33..41 + 0: COLON@33..35 ":" [] [Whitespace(" ")] + 1: TS_STRING_TYPE@35..41 + 0: STRING_KW@35..41 "string" [] [] + 3: (empty) + 2: R_PAREN@41..43 ")" [] [Whitespace(" ")] + 3: JS_FUNCTION_BODY@43..45 + 0: L_CURLY@43..44 "{" [] [] + 1: JS_DIRECTIVE_LIST@44..44 + 2: JS_STATEMENT_LIST@44..44 + 3: R_CURLY@44..45 "}" [] [] + 9: R_CURLY@45..47 "}" [Newline("\n")] [] + 3: EOF@47..48 "" [Newline("\n")] [] diff --git a/crates/rome_js_parser/test_data/inline/err/decorator_parameters.ts b/crates/rome_js_parser/test_data/inline/ok/decorator_parameters_constructor.ts similarity index 100% rename from crates/rome_js_parser/test_data/inline/err/decorator_parameters.ts rename to crates/rome_js_parser/test_data/inline/ok/decorator_parameters_constructor.ts diff --git a/crates/rome_js_parser/test_data/inline/ok/ts_formal_parameter_decorator.rast b/crates/rome_js_parser/test_data/inline/ok/ts_formal_parameter_decorator.rast new file mode 100644 index 00000000000..eb286327685 --- /dev/null +++ b/crates/rome_js_parser/test_data/inline/ok/ts_formal_parameter_decorator.rast @@ -0,0 +1,193 @@ +JsModule { + interpreter_token: missing (optional), + directives: JsDirectiveList [], + items: JsModuleItemList [ + JsFunctionDeclaration { + async_token: missing (optional), + function_token: FUNCTION_KW@0..9 "function" [] [Whitespace(" ")], + star_token: missing (optional), + id: JsIdentifierBinding { + name_token: IDENT@9..10 "a" [] [], + }, + type_parameters: missing (optional), + parameters: JsParameters { + l_paren_token: L_PAREN@10..11 "(" [] [], + items: JsParameterList [ + JsFormalParameter { + binding: JsIdentifierBinding { + name_token: IDENT@11..17 "x" [Skipped("@"), Skipped("dec"), Whitespace(" ")] [], + }, + question_mark_token: missing (optional), + type_annotation: missing (optional), + initializer: missing (optional), + }, + ], + r_paren_token: R_PAREN@17..19 ")" [] [Whitespace(" ")], + }, + return_type_annotation: missing (optional), + body: JsFunctionBody { + l_curly_token: L_CURLY@19..20 "{" [] [], + directives: JsDirectiveList [], + statements: JsStatementList [], + r_curly_token: R_CURLY@20..21 "}" [] [], + }, + }, + JsClassDeclaration { + decorators: JsDecoratorList [], + abstract_token: missing (optional), + class_token: CLASS_KW@21..28 "class" [Newline("\n")] [Whitespace(" ")], + id: JsIdentifierBinding { + name_token: IDENT@28..32 "Foo" [] [Whitespace(" ")], + }, + type_parameters: missing (optional), + extends_clause: missing (optional), + implements_clause: missing (optional), + l_curly_token: L_CURLY@32..33 "{" [] [], + members: JsClassMemberList [ + JsConstructorClassMember { + modifiers: JsConstructorModifierList [], + name: JsLiteralMemberName { + value: IDENT@33..48 "constructor" [Newline("\n"), Whitespace(" ")] [], + }, + parameters: JsConstructorParameters { + l_paren_token: L_PAREN@48..49 "(" [] [], + parameters: JsConstructorParameterList [ + JsFormalParameter { + binding: JsIdentifierBinding { + name_token: IDENT@49..55 "x" [Skipped("@"), Skipped("dec"), Whitespace(" ")] [], + }, + question_mark_token: missing (optional), + type_annotation: missing (optional), + initializer: missing (optional), + }, + ], + r_paren_token: R_PAREN@55..57 ")" [] [Whitespace(" ")], + }, + body: JsFunctionBody { + l_curly_token: L_CURLY@57..58 "{" [] [], + directives: JsDirectiveList [], + statements: JsStatementList [], + r_curly_token: R_CURLY@58..59 "}" [] [], + }, + }, + JsMethodClassMember { + modifiers: JsMethodModifierList [], + async_token: missing (optional), + star_token: missing (optional), + name: JsLiteralMemberName { + value: IDENT@59..69 "method" [Newline("\n"), Whitespace(" ")] [], + }, + question_mark_token: missing (optional), + type_parameters: missing (optional), + parameters: JsParameters { + l_paren_token: L_PAREN@69..70 "(" [] [], + items: JsParameterList [ + JsFormalParameter { + binding: JsIdentifierBinding { + name_token: IDENT@70..76 "x" [Skipped("@"), Skipped("dec"), Whitespace(" ")] [], + }, + question_mark_token: missing (optional), + type_annotation: missing (optional), + initializer: missing (optional), + }, + ], + r_paren_token: R_PAREN@76..78 ")" [] [Whitespace(" ")], + }, + return_type_annotation: missing (optional), + body: JsFunctionBody { + l_curly_token: L_CURLY@78..79 "{" [] [], + directives: JsDirectiveList [], + statements: JsStatementList [], + r_curly_token: R_CURLY@79..80 "}" [] [], + }, + }, + ], + r_curly_token: R_CURLY@80..82 "}" [Newline("\n")] [], + }, + ], + eof_token: EOF@82..83 "" [Newline("\n")] [], +} + +0: JS_MODULE@0..83 + 0: (empty) + 1: JS_DIRECTIVE_LIST@0..0 + 2: JS_MODULE_ITEM_LIST@0..82 + 0: JS_FUNCTION_DECLARATION@0..21 + 0: (empty) + 1: FUNCTION_KW@0..9 "function" [] [Whitespace(" ")] + 2: (empty) + 3: JS_IDENTIFIER_BINDING@9..10 + 0: IDENT@9..10 "a" [] [] + 4: (empty) + 5: JS_PARAMETERS@10..19 + 0: L_PAREN@10..11 "(" [] [] + 1: JS_PARAMETER_LIST@11..17 + 0: JS_FORMAL_PARAMETER@11..17 + 0: JS_IDENTIFIER_BINDING@11..17 + 0: IDENT@11..17 "x" [Skipped("@"), Skipped("dec"), Whitespace(" ")] [] + 1: (empty) + 2: (empty) + 3: (empty) + 2: R_PAREN@17..19 ")" [] [Whitespace(" ")] + 6: (empty) + 7: JS_FUNCTION_BODY@19..21 + 0: L_CURLY@19..20 "{" [] [] + 1: JS_DIRECTIVE_LIST@20..20 + 2: JS_STATEMENT_LIST@20..20 + 3: R_CURLY@20..21 "}" [] [] + 1: JS_CLASS_DECLARATION@21..82 + 0: JS_DECORATOR_LIST@21..21 + 1: (empty) + 2: CLASS_KW@21..28 "class" [Newline("\n")] [Whitespace(" ")] + 3: JS_IDENTIFIER_BINDING@28..32 + 0: IDENT@28..32 "Foo" [] [Whitespace(" ")] + 4: (empty) + 5: (empty) + 6: (empty) + 7: L_CURLY@32..33 "{" [] [] + 8: JS_CLASS_MEMBER_LIST@33..80 + 0: JS_CONSTRUCTOR_CLASS_MEMBER@33..59 + 0: JS_CONSTRUCTOR_MODIFIER_LIST@33..33 + 1: JS_LITERAL_MEMBER_NAME@33..48 + 0: IDENT@33..48 "constructor" [Newline("\n"), Whitespace(" ")] [] + 2: JS_CONSTRUCTOR_PARAMETERS@48..57 + 0: L_PAREN@48..49 "(" [] [] + 1: JS_CONSTRUCTOR_PARAMETER_LIST@49..55 + 0: JS_FORMAL_PARAMETER@49..55 + 0: JS_IDENTIFIER_BINDING@49..55 + 0: IDENT@49..55 "x" [Skipped("@"), Skipped("dec"), Whitespace(" ")] [] + 1: (empty) + 2: (empty) + 3: (empty) + 2: R_PAREN@55..57 ")" [] [Whitespace(" ")] + 3: JS_FUNCTION_BODY@57..59 + 0: L_CURLY@57..58 "{" [] [] + 1: JS_DIRECTIVE_LIST@58..58 + 2: JS_STATEMENT_LIST@58..58 + 3: R_CURLY@58..59 "}" [] [] + 1: JS_METHOD_CLASS_MEMBER@59..80 + 0: JS_METHOD_MODIFIER_LIST@59..59 + 1: (empty) + 2: (empty) + 3: JS_LITERAL_MEMBER_NAME@59..69 + 0: IDENT@59..69 "method" [Newline("\n"), Whitespace(" ")] [] + 4: (empty) + 5: (empty) + 6: JS_PARAMETERS@69..78 + 0: L_PAREN@69..70 "(" [] [] + 1: JS_PARAMETER_LIST@70..76 + 0: JS_FORMAL_PARAMETER@70..76 + 0: JS_IDENTIFIER_BINDING@70..76 + 0: IDENT@70..76 "x" [Skipped("@"), Skipped("dec"), Whitespace(" ")] [] + 1: (empty) + 2: (empty) + 3: (empty) + 2: R_PAREN@76..78 ")" [] [Whitespace(" ")] + 7: (empty) + 8: JS_FUNCTION_BODY@78..80 + 0: L_CURLY@78..79 "{" [] [] + 1: JS_DIRECTIVE_LIST@79..79 + 2: JS_STATEMENT_LIST@79..79 + 3: R_CURLY@79..80 "}" [] [] + 9: R_CURLY@80..82 "}" [Newline("\n")] [] + 3: EOF@82..83 "" [Newline("\n")] [] diff --git a/crates/rome_js_parser/test_data/inline/err/ts_formal_parameter_decorator.ts b/crates/rome_js_parser/test_data/inline/ok/ts_formal_parameter_decorator.ts similarity index 100% rename from crates/rome_js_parser/test_data/inline/err/ts_formal_parameter_decorator.ts rename to crates/rome_js_parser/test_data/inline/ok/ts_formal_parameter_decorator.ts