Skip to content

Commit

Permalink
fix(transformer/class-properties): panic when the callee or member is…
Browse files Browse the repository at this point in the history
… ParenthesisExpression or TS-syntax expressions.
  • Loading branch information
Dunqing committed Dec 11, 2024
1 parent 4a524ed commit 86bc6d2
Show file tree
Hide file tree
Showing 10 changed files with 102 additions and 10 deletions.
11 changes: 5 additions & 6 deletions crates/oxc_transformer/src/es2022/class_properties/private.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1001,7 +1001,6 @@ impl<'a, 'ctx> ClassProperties<'a, 'ctx> {
expr: &mut Expression<'a>,
ctx: &mut TraverseCtx<'a>,
) -> Option<Expression<'a>> {
assert_expr_neither_parenthesis_nor_typescript_syntax(expr);
match expr {
Expression::PrivateFieldExpression(_) => {
Some(self.transform_private_field_expression_of_chain_expression(expr, ctx))
Expand All @@ -1015,7 +1014,7 @@ impl<'a, 'ctx> ClassProperties<'a, 'ctx> {
self.transform_call_expression_of_chain_expression(call, ctx)
}
_ => {
assert_expr_neither_parenthesis_nor_typescript_syntax(expr);
assert_expr_neither_parenthesis_nor_typescript_syntax(expr, &self.ctx.source_path);
None
}
}
Expand Down Expand Up @@ -1126,7 +1125,7 @@ impl<'a, 'ctx> ClassProperties<'a, 'ctx> {
ctx: &mut TraverseCtx<'a>,
) -> Option<Expression<'a>> {
let is_optional = member.optional();
let object = member.object_mut();
let object = member.object_mut().get_inner_expression_mut();
let result = self.transform_chain_element_recursively(object, ctx)?;
if is_optional && !object.is_identifier_reference() {
// `o?.Foo.#self.self?.self.unicorn;` -> `(result ? void 0 : object)?.self.unicorn`
Expand Down Expand Up @@ -1320,7 +1319,7 @@ impl<'a, 'ctx> ClassProperties<'a, 'ctx> {
let callee = &mut call.callee;
let callee_member = callee.to_member_expression_mut();
let is_optional_callee = callee_member.optional();
let object = callee_member.object_mut();
let object = callee_member.object_mut().get_inner_expression_mut();

let context = if let Some(result) = self.transform_chain_element_recursively(object, ctx) {
if is_optional_callee {
Expand Down Expand Up @@ -1609,7 +1608,7 @@ impl<'a, 'ctx> ClassProperties<'a, 'ctx> {
object: Expression<'a>,
ctx: &mut TraverseCtx<'a>,
) -> (Expression<'a>, Expression<'a>) {
assert_expr_neither_parenthesis_nor_typescript_syntax(&object);
assert_expr_neither_parenthesis_nor_typescript_syntax(&object, &self.ctx.source_path);
self.ctx.duplicate_expression(object, false, ctx)
}

Expand All @@ -1628,7 +1627,7 @@ impl<'a, 'ctx> ClassProperties<'a, 'ctx> {
object: Expression<'a>,
ctx: &mut TraverseCtx<'a>,
) -> (Expression<'a>, Expression<'a>, Expression<'a>) {
assert_expr_neither_parenthesis_nor_typescript_syntax(&object);
assert_expr_neither_parenthesis_nor_typescript_syntax(&object, &self.ctx.source_path);
self.ctx.duplicate_expression_twice(object, false, ctx)
}

Expand Down
9 changes: 7 additions & 2 deletions crates/oxc_transformer/src/es2022/class_properties/utils.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
//! ES2022: Class Properties
//! Utility functions.
use std::path::PathBuf;

use oxc_ast::ast::*;
use oxc_span::SPAN;
use oxc_syntax::reference::ReferenceFlags;
Expand Down Expand Up @@ -55,9 +57,12 @@ pub(super) fn create_underscore_ident_name<'a>(ctx: &mut TraverseCtx<'a>) -> Ide
}

#[inline]
pub(super) fn assert_expr_neither_parenthesis_nor_typescript_syntax(expr: &Expression) {
pub(super) fn assert_expr_neither_parenthesis_nor_typescript_syntax(
expr: &Expression,
path: &PathBuf,
) {
debug_assert!(
!(matches!(expr, Expression::ParenthesizedExpression(_)) || expr.is_typescript_syntax()),
"Should not be: {expr:?}",
"Should not be: {expr:?} in {path:?}",
);
}
23 changes: 21 additions & 2 deletions tasks/transform_conformance/snapshots/oxc.snap.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
commit: 54a8389f

Passed: 103/117
Passed: 104/120

# All Passed:
* babel-plugin-transform-class-static-block
Expand All @@ -16,7 +16,7 @@ Passed: 103/117
* regexp


# babel-plugin-transform-class-properties (4/7)
# babel-plugin-transform-class-properties (5/10)
* private-loose-tagged-template/input.js
Scope children mismatch:
after transform: ScopeId(1): [ScopeId(2), ScopeId(3), ScopeId(4)]
Expand Down Expand Up @@ -62,6 +62,25 @@ Scope parent mismatch:
after transform: ScopeId(20): Some(ScopeId(1))
rebuilt : ScopeId(20): Some(ScopeId(0))

* typescript/optional-call/input.ts
Scope children mismatch:
after transform: ScopeId(0): [ScopeId(1)]
rebuilt : ScopeId(0): [ScopeId(1), ScopeId(3)]
Scope children mismatch:
after transform: ScopeId(1): [ScopeId(2), ScopeId(3)]
rebuilt : ScopeId(1): [ScopeId(2)]
Scope parent mismatch:
after transform: ScopeId(2): Some(ScopeId(1))
rebuilt : ScopeId(3): Some(ScopeId(0))
Symbol reference IDs mismatch for "X":
after transform: SymbolId(0): [ReferenceId(0), ReferenceId(2), ReferenceId(6), ReferenceId(11), ReferenceId(16)]
rebuilt : SymbolId(0): [ReferenceId(0), ReferenceId(2), ReferenceId(8), ReferenceId(14)]

* typescript/optional-member/input.ts
Symbol reference IDs mismatch for "X":
after transform: SymbolId(0): [ReferenceId(0), ReferenceId(2), ReferenceId(6), ReferenceId(9), ReferenceId(12)]
rebuilt : SymbolId(0): [ReferenceId(0), ReferenceId(2), ReferenceId(6), ReferenceId(10)]


# babel-plugin-transform-async-to-generator (14/15)
* super/nested/input.js
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
class A {
static #a = 33;
b = 44;
method() {
(undefined, this)?.#a;
(undefined, this)?.b;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
class A {
constructor() {
babelHelpers.defineProperty(this, "b", 44);
}
method() {
var _ref;
(_ref = (undefined, this)) === null || _ref === void 0 ? void 0 : babelHelpers.assertClassBrand(A, _ref, _a)._;
(undefined, this)?.b;
}
}
var _a = {
_: 33
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
class X {
static #m = () => {};
method() {
const o = { X };
(o.X as typeof X).#m();
o.X!.#m();
o.X.#m();
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
class X {
method() {
var _o$X, _o$X2, _o$X3;
const o = {
X
};
babelHelpers.assertClassBrand(X, _o$X = o.X, _m)._.call(_o$X);
babelHelpers.assertClassBrand(X, _o$X2 = o.X, _m)._.call(_o$X2);
babelHelpers.assertClassBrand(X, _o$X3 = o.X, _m)._.call(_o$X3);
}
}
var _m = {
_: () => {}
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
class X {
static #a = 0;
method() {
const o = { X };
(o.X as typeof X).#a;
o.X!.#a;
o.X.#a;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
class X {
method() {
const o = {
X
};
babelHelpers.assertClassBrand(X, o.X, _a)._;
babelHelpers.assertClassBrand(X, o.X, _a)._;
babelHelpers.assertClassBrand(X, o.X, _a)._;
}
}
var _a = {
_: 0
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
{
"plugins": ["transform-class-properties", "transform-typescript"]
}

0 comments on commit 86bc6d2

Please sign in to comment.