You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

TypeScript中可选字段对象的Deep Keyof失效问题求助

解决可选对象字段下的深度keyof类型推导问题

当对象中的字段为可选类型时,使用keyof进行深度类型推导会失效。比如以下代码中,Post字段是可选的,导致调用select函数时,select对象内无法正确提示id和content字段:

type Database = {
    User?: {
        id: string
        name: string
    },
    Post?: {   // 移除?后可正常工作,但该字段需为可选
        id: string
        content: string
    }
}

type SelectQuery<T> = {
    [Table in keyof T]?: {
        select: {
            [field in keyof T[Table]]?: boolean
        }
    }
}

function select(query: SelectQuery<Database>) {}

select({
    Post: {
        select: {
          // 此处本应提示content和id字段,但无任何提示
        }
    }
})

解决方案

问题根源在于:可选字段的类型是对应对象类型 | undefined,而keyof undefined的结果是never,自然无法推导出内部字段名。我们需要用NonNullable<T[Table]>先剔除undefined类型,再获取其keyof:

修改后的SelectQuery类型如下:

type SelectQuery<T> = {
    [Table in keyof T]?: {
        select: {
            [field in keyof NonNullable<T[Table]>]?: boolean
        }
    }
}

完整的可运行代码:

type Database = {
    User?: {
        id: string
        name: string
    },
    Post?: {
        id: string
        content: string
    }
}

type SelectQuery<T> = {
    [Table in keyof T]?: {
        select: {
            [field in keyof NonNullable<T[Table]>]?: boolean
        }
    }
}

function select(query: SelectQuery<Database>) {}

select({
    Post: {
        select: {
          id: true, // 现在能正确提示id和content
          content: false
        }
    }
})

NonNullable<T>是TypeScript内置工具类型,用于从类型T中剔除null和undefined,这样我们就能准确获取到可选字段内部对象的所有键名,实现预期的类型提示效果。

内容的提问来源于stack exchange,提问作者Mr.Trieu

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.14 12:52:17