'Create child class object from parent class static method typescript
I have two classes User
and Model
User class extends Base class Model.
class User extends Model {}
Model class has a static method createFrom
static createFrom<T, K>(this: new () => T, data: K): T {}
I can call this method like
User.createFrom<User, DataType>({...data_of_DataType});
User.createFrom<User, OtherDataType>({...data_of_OtherDataType});
As you can see I have to define User
in generics everytime when I have to add generic DataType
I want something like this.
User.createFrom<DataType>({...data_of_DataType});
Is it possible without removing generic T
from createFrom
because I need return type in createFrom
Update.
Here is Minimal Reproducible Example you can check it
update 2
// Lib
function convertDataIntoClass(cls: any, data: any){
// convert data into class obj and return
return cls;
}
// End Lib
class Model {
static createFrom<T, K>(this: new () => T, data: K): T {
return convertDataIntoClass(this, data);
}
}
class User extends Model {}
interface IData {
id: string;
}
interface IAnotherData {
name: string;
}
const anotherData: IAnotherData = {name: "id-123"};
const data: IData = {id: "id-123"};
// It work like this
User.createFrom<User, IData>(data);
// You can't create with other data
User.createFrom<User, IData>(anotherData); // Error, this is what I want
// Create user with other type
User.createFrom<User, IAnotherData>(anotherData);
// I want something like this
User.createFrom<IData>(data);
As you can see in example if you explicitly define the data type then you can't use anyother data type. For example User.createFrom<User, IData>(anotherData)
if you define IData
you can't use anotherData
init and vice versa. This is what I want just I don't want to pass User
everytime in createFrom
generic I simple want something like User.createFrom<IData>(data)
Solution 1:[1]
You don't need any explicit type parameters. TS is smart enough to infer both the class and data type from the call signature:
User.createFrom(data);
// Model.createFrom<User, IData>(this: new () => User, data: IData): User
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | lawrence-witt |