-
-
Notifications
You must be signed in to change notification settings - Fork 932
Closed
Labels
A-transformerArea - Transformer / TranspilerArea - Transformer / TranspilerC-bugCategory - BugCategory - Bug
Description
In TypeScript, the following class (case 1) reports a type error:
class Foo {
x = this.foo // error: Property 'foo' is used before its initialization
foo: any
constructor(foo: any) {
this.foo = foo
}
}Because it will be transformed to:
class Foo {
constructor(foo) {
this.x = this.foo; // <-- this.foo not assigned yet!
this.foo = foo;
}
}However, if it uses access modifier on the constructor argument (case 2):
class Foo {
x = this.foo
constructor(public foo: any) {
console.log(this.foo)
}
}It will work both in types and at runtime, because it will be transformed to:
class Foo {
constructor(foo) {
this.foo = foo; // <-- injected from argument
this.x = this.foo; // <-- moved from field initializers
console.log(this.foo);
}
}Notice how x = this.foo is moved into the constructor to be after the this.foo assignment.
Oxc's current behavior
Oxc currently transforms case 2 to:
class Foo {
x = this.foo
constructor(foo) {
console.log(this.foo)
this.foo = foo // <-- injected from argument
}
}Notice that both x = this.foo and console.log(this.foo) are executed before the this.foo assignment, both leading to runtime errors.
What needs to be fixed
- The generated assignment for constructor arguments with access modifiers should be injected to the top of the constructor, not the bottom.
- When constructor argument access modifiers are used, all class field initializers need to be moved into the constructor (so their initialization order is preserved), after the argument assignments, and before existing constructor code.
Related: Behavior with useDefineForClassFields: true
When useDefineForClassFields is set to true, case 2 will also throw a type error. And TS's transform out will become:
class Foo {
foo;
x = this.foo;
constructor(foo) {
this.foo = foo;
console.log(this.foo);
}
}I'm not sure if oxc's TS transform currently takes this into account, but this is something we will need to consider.
Reactions are currently unavailable
Metadata
Metadata
Assignees
Labels
A-transformerArea - Transformer / TranspilerArea - Transformer / TranspilerC-bugCategory - BugCategory - Bug
Type
Fields
Give feedbackPriority
None yet