When constraining a generic type for a class, ts complains that the generic could be instantiated with a different subtype. Anyone have any idea what that actually means (and what to do about it)?
Reproduction (TypeScript 3.6.4):
interface BaseSchema {
readonly id: string;
}
class Model<GenericSchema extends BaseSchema> {
public test(): GenericSchema {
return { id: '' };
}
}
Error:
Type '{ id: string; }' is not assignable to type 'GenericSchema'. '{ id: string; }' is assignable to the constraint of type 'GenericSchema', but 'GenericSchema' could be instantiated with a different subtype of constraint 'BaseSchema'.ts(2322)
Seems to be related to https://www.typescriptlang.org/docs/handbook/release-notes/typescript-2-6.html#strict-function-types
I can make it work with a type assertion, but it does not seem right:
interface BaseSchema {
readonly id: string;
}
export class Model<GenericSchema extends BaseSchema> {
public test2(): GenericSchema {
return { id: '' } as GenericSchema;
}
}
UPDATE: New example below. In the example we provide a generic MySchema when instantiating Model, and this expect the test() method to return MySchema.
class Model<
GenericSchema extends {
readonly id: string;
}
> {
public test() {
const dbResult: GenericSchema = { id: '' };
return dbResult;
}
}
interface MySchema {
readonly id: string;
readonly name: string;
}
const model = new Model<MySchema>();
const schema: MySchema = model.test();
These are all contrived examples, the real use case is to access a DB and return data for which I have type annotations. Essentially MySchema would represent the data model in the database, so I want to provide it as a generic (since TS can't possibly know what the data looks like in the DB otherwise).