diff --git a/crates/swc_ecma_parser/src/error.rs b/crates/swc_ecma_parser/src/error.rs index cf6f8d655f3c..c61d04b0ab73 100644 --- a/crates/swc_ecma_parser/src/error.rs +++ b/crates/swc_ecma_parser/src/error.rs @@ -279,6 +279,7 @@ pub enum SyntaxError { TS2703, TS4112, TS8038, + TS18010, TSTypeAnnotationAfterAssign, TsNonNullAssertionNotAllowed(JsWord), @@ -720,6 +721,9 @@ impl SyntaxError { SyntaxError::TS8038 => "Decorators may not appear after `export` or `export default` \ if they also appear before `export`." .into(), + SyntaxError::TS18010 => { + "An accessibility modifier cannot be used with a private identifier.".into() + } SyntaxError::TSTypeAnnotationAfterAssign => { "Type annotations must come before default assignments".into() } diff --git a/crates/swc_ecma_parser/src/parser/class_and_fn.rs b/crates/swc_ecma_parser/src/parser/class_and_fn.rs index 9962b6ac77d5..fce10ad3e4f5 100644 --- a/crates/swc_ecma_parser/src/parser/class_and_fn.rs +++ b/crates/swc_ecma_parser/src/parser/class_and_fn.rs @@ -1097,20 +1097,27 @@ impl Parser { } Ok(match key { - Key::Private(key) => PrivateProp { - span: span!(p, start), - key, - value, - is_static, - decorators, - accessibility, - is_optional, - is_override, - readonly, - type_ann, - definite, + Key::Private(key) => { + let span = span!(p, start); + if accessibility.is_some() { + p.emit_err(span.with_hi(key.span_hi()), SyntaxError::TS18010); + } + + PrivateProp { + span: span!(p, start), + key, + value, + is_static, + decorators, + accessibility, + is_optional, + is_override, + readonly, + type_ann, + definite, + } + .into() } - .into(), Key::Public(key) => { let span = span!(p, start); if is_abstract && value.is_some() { @@ -1446,20 +1453,27 @@ impl Parser { } match key { - Key::Private(key) => Ok(PrivateMethod { - span: span!(self, start), + Key::Private(key) => { + let span = span!(self, start); + if accessibility.is_some() { + self.emit_err(span.with_hi(key.span_hi()), SyntaxError::TS18010); + } - accessibility, - is_abstract, - is_optional, - is_override, + Ok(PrivateMethod { + span, - is_static, - key, - function, - kind, + accessibility, + is_abstract, + is_optional, + is_override, + + is_static, + key, + function, + kind, + } + .into()) } - .into()), Key::Public(key) => { let span = span!(self, start); if is_abstract && function.body.is_some() { diff --git a/crates/swc_ecma_parser/tests/errors/issue-8687/input.ts b/crates/swc_ecma_parser/tests/errors/issue-8687/input.ts new file mode 100644 index 000000000000..3e8eacea5842 --- /dev/null +++ b/crates/swc_ecma_parser/tests/errors/issue-8687/input.ts @@ -0,0 +1,4 @@ +class Foo { + private #p1() { } + private #p2: number; +} \ No newline at end of file diff --git a/crates/swc_ecma_parser/tests/errors/issue-8687/input.ts.swc-stderr b/crates/swc_ecma_parser/tests/errors/issue-8687/input.ts.swc-stderr new file mode 100644 index 000000000000..d74069efea60 --- /dev/null +++ b/crates/swc_ecma_parser/tests/errors/issue-8687/input.ts.swc-stderr @@ -0,0 +1,16 @@ + + x An accessibility modifier cannot be used with a private identifier. + ,-[$DIR/tests/errors/issue-8687/input.ts:1:1] + 1 | class Foo { + 2 | private #p1() { } + : ^^^^^^^^^^^ + 3 | private #p2: number; + `---- + + x An accessibility modifier cannot be used with a private identifier. + ,-[$DIR/tests/errors/issue-8687/input.ts:2:1] + 2 | private #p1() { } + 3 | private #p2: number; + : ^^^^^^^^^^^ + 4 | } + `---- diff --git a/crates/swc_ecma_transforms_typescript/src/strip_type.rs b/crates/swc_ecma_transforms_typescript/src/strip_type.rs index 1680a866a293..2cc2db1cafce 100644 --- a/crates/swc_ecma_transforms_typescript/src/strip_type.rs +++ b/crates/swc_ecma_transforms_typescript/src/strip_type.rs @@ -89,6 +89,14 @@ impl VisitMut for StripType { prop.visit_mut_children_with(self); } + fn visit_mut_private_method(&mut self, n: &mut PrivateMethod) { + n.accessibility = None; + n.is_abstract = false; + n.is_optional = false; + n.is_override = false; + n.visit_mut_children_with(self); + } + fn visit_mut_constructor(&mut self, n: &mut Constructor) { n.accessibility = None; n.visit_mut_children_with(self);