TypeScript中如何在另一类型中使用父类型的值?(ORM场景)
问题描述
我正在尝试编写一个简易ORM,代码如下:
type Models = { User: { name: string }, Template: { text: string } } type ExtractKeysFrom<T> = keyof T type ModelsKeys = ExtractKeysFrom<Models, Object> // 正确返回:'User' | 'Template' type ORM = { model: (modelName: ModelsKeys) => { create(props: Models[typeof modelName]): Promise<boolean> } }
实现代码:
declare const orm: () => ORM; orm().model('User').create({ name: 'Adam' })
我希望create()中的props能自动匹配对应模型(比如User)的属性,但当前得到的是:
create(props: User | Template): Promise<boolean>
我知道typeof modelName的写法有误,应该用extends进行类型检查,但不清楚具体实现方式,能否提供建议?
解决方案
问题核心是model方法没有通过泛型建立传入参数与返回值的类型关联,导致TypeScript无法精准推导create的参数类型。你需要将model定义为泛型方法,用泛型约束绑定模型名和对应的数据结构。
修改后的类型定义如下:
type Models = { User: { name: string }, Template: { text: string } } // 简化类型定义,直接用keyof Models获取模型键集合 type ModelsKeys = keyof Models; type ORM = { // 泛型K约束为Models的键类型 model<K extends ModelsKeys>(modelName: K): { // 通过K索引Models,精准获取对应模型的属性类型 create(props: Models[K]): Promise<boolean> } }
修改后,调用orm().model('User').create(...)时,TypeScript会自动推导props必须符合User的结构;调用model('Template')时,props则会匹配Template的类型,不会再出现联合类型的问题。
内容的提问来源于stack exchange,提问作者Greg Wozniak
相关产品推荐
相关产品推荐

