如何使用变量来推断打字稿中的对象

时间:2020-05-23 18:38:43

标签: typescript

我有以下正在运行的代码:

type ParamType = { a: string, b: string } | { c: string }

if ('a' in params) {
  doSomethingA(params)
} else {
  doSomethingC(params)
}

doSomethingA仅接受{ a: string, b: string },而doSomethingC仅接受{ c: string }

我遇到的问题是我最近更改了{ a: string, b: string }中的键,而打字稿并未像我希望的那样抱怨'a' in params。因此,我进行了以下更新:

type A = { a: string, d: string }
type B = { c: string }
type ParamType = A | B

const testKey: keyof A = 'd'

if (testKey in params) {
  doSomethingA(params)
} else {
  doSomethingC(params)
}

但是现在,打字稿无法在if / else中正确推断params的类型,我得到:

Property 'd' is missing in type 'B' but required in type 'A'.

Is there a way to ensure that the key I'm using in my if statement is one of the keys from A while also getting correct types within the if statement itself?

1 个答案:

答案 0 :(得分:0)

我认为TypeScript没有该功能(还可以吗?)。如您所见,if ('d' in params) {可以缩小if分支的类型,但是即使const testKey = 'd'; if (testKey in params) {testKey的类型完全相同,即使'd'也不起作用这种情况。

您可以创建用于检查键的自定义类型保护功能,但是您必须实现它,并在实现中重复为类型定义的键,因为类型不会跟随运行时代码

type A = { a: string, d: string }
type B = { c: string }
type ParamType = A | B

function isA(ob:A|B, key:keyof A | keyof B): ob is A {
    return new Set(['a', 'd']).has(key);
}

const g = (params:ParamType) =>  {
    const testKey:keyof A = 'a'

    if (isA(params, testKey)) {
        doSomethingD(params)
    } else {
        doSomethingC(params)
    }
}