Although not initially intuitive, I run into this issue while documenting the register
function in Marty.js. I didn't realise a solution, so I reached out to a friend who provided me with this beauty.
function register<T>(clazz: { new (...args: any[]): T }): T;
And it works brilliantly! But what's this even doing? I've just created a generic function that accepts a constructor function of any type and returns that type. No need to do type coercion. It turned out perfectly for this situation, where I can register a Store
, Queries
, ActionCreators
and more!
You can also write this with a slightly different syntax such as new (...args: any[]) => T
. There's no real difference here.
Although it doesn't apply here, we can also look how we might accept more specific types of constructors.
// Using `typeof`...
class X {
method(): void {}
}
function create(C: typeof X) {
return new C();
}
create(X);
// Using an inline parameter...
interface Y {
method(): void;
}
function create2(C: new (...args: any[]) => Y) {
return new C();
}
class Z implements Y {
method(): void {}
}
create2(Z);
Questions? Find me on Twitter or open an issue.