Describe the bug
We are migrating from vite 5.2 to the latest version, while doing so, I had everything working until I went to run the app and some of our pages were broken. After doing some research, it appears that vite 5.2 was also broken, but not in all circumstances but vite 8.x is in all when using accessor and private constructor variables, the accessor is invoked before the constructor variable is set, which is different from how typescript compilation works.
Reproduction
N/A
Steps to reproduce
Code Sample that works on 5.2 but not on 8.x
class CoursesApi {
onClearFilters() {
}
}
class Hello {
constructor(private input: { onRefresh: () => void, onClearFilters: () => void }) {
}
private api = new CoursesApi();
accessor util = {
onRefresh: this.input.onRefresh,
onClearFilters: this.input.onClearFilters
};
}
var hello = new Hello({ onRefresh: () => { }, onClearFilters: () => { } })
console.log(hello);
Code Sample 2 which doesn't work on 5.2 or 8.x
class Hello {
constructor(private input: { onRefresh: () => void, onClearFilters: () => void }) {
}
accessor util = {
onRefresh: this.input.onRefresh,
onClearFilters: this.input.onClearFilters
};
}
var hello = new Hello({ onRefresh: () => { }, onClearFilters: () => { } })
console.log(hello);
The problem with Code Sample 1 is that on vite 8.x it outputs like this:
var Hello = class {
constructor(input) {
this.input = input;
this.api = new CoursesApi();
}
#A = {
onRefresh: this.input.onRefresh,
onClearFilters: this.api.onClearFilters
};
get util() {
return this.#A;
}
set util(v) {
this.#A = v;
}
};
on 5.2 it outputs like this
class Hello {
constructor(input) {
__privateAdd(this, _A);
this.input = input;
this.api = new CoursesApi();
__privateSet(this, _A, {
onRefresh: this.input.onRefresh,
onClearFilters: this.input.onClearFilters
});
}
get util() {
return __privateGet(this, _A);
}
set util(v) {
__privateSet(this, _A, v);
}
This doesn't access this.input until this.input is actually set.
For reference typescript compiles it like this:
class Hello {
constructor(input) {
this.input = input;
this.api = new CoursesApi();
_Hello_util_accessor_storage.set(this, {
onRefresh: this.input.onRefresh,
onClearFilters: this.input.onClearFilters
});
}
get util() { return __classPrivateFieldGet(this, _Hello_util_accessor_storage, "f"); }
set util(value) { __classPrivateFieldSet(this, _Hello_util_accessor_storage, value, "f"); }
}
If you remove the api = field on the class, then 5.2 and 8.x fail, because 5.2 then adds the creation of the method directly in __privateAdd instead of the Set method before input is set.
How do we get vite to output the code so that it sets this.input correctly before creating the object that uses it. I would say that is "Correct" becaus that is what the typescript compiler does.
System Info
System:
OS: Windows 11 10.0.26100
CPU: (16) x64 Intel(R) Core(TM) Ultra 9 285H
Memory: 32.82 GB / 63.43 GB
Binaries:
Node: 25.3.0 - C:\Program Files\nodejs\node.EXE
Yarn: 1.22.22 - C:\Users\michael.paulus\AppData\Roaming\npm\yarn.CMD
npm: 11.6.2 - C:\Program Files\nodejs\npm.CMD
pnpm: 10.32.1 - C:\Users\michael.paulus\AppData\Roaming\npm\pnpm.CMD
Browsers:
Edge: Chromium (143.0.3650.139)
Used Package Manager
pnpm
Logs
No response
Validations
Describe the bug
We are migrating from vite 5.2 to the latest version, while doing so, I had everything working until I went to run the app and some of our pages were broken. After doing some research, it appears that vite 5.2 was also broken, but not in all circumstances but vite 8.x is in all when using accessor and private constructor variables, the accessor is invoked before the constructor variable is set, which is different from how typescript compilation works.
Reproduction
N/A
Steps to reproduce
Code Sample that works on 5.2 but not on 8.x
Code Sample 2 which doesn't work on 5.2 or 8.x
The problem with Code Sample 1 is that on vite 8.x it outputs like this:
on 5.2 it outputs like this
This doesn't access this.input until this.input is actually set.
For reference typescript compiles it like this:
If you remove the api = field on the class, then 5.2 and 8.x fail, because 5.2 then adds the creation of the method directly in __privateAdd instead of the Set method before input is set.
How do we get vite to output the code so that it sets this.input correctly before creating the object that uses it. I would say that is "Correct" becaus that is what the typescript compiler does.
System Info
System: OS: Windows 11 10.0.26100 CPU: (16) x64 Intel(R) Core(TM) Ultra 9 285H Memory: 32.82 GB / 63.43 GB Binaries: Node: 25.3.0 - C:\Program Files\nodejs\node.EXE Yarn: 1.22.22 - C:\Users\michael.paulus\AppData\Roaming\npm\yarn.CMD npm: 11.6.2 - C:\Program Files\nodejs\npm.CMD pnpm: 10.32.1 - C:\Users\michael.paulus\AppData\Roaming\npm\pnpm.CMD Browsers: Edge: Chromium (143.0.3650.139)Used Package Manager
pnpm
Logs
No response
Validations