我正在尝试编写一个可以接收几个相似对象的函数。像这样:
SELECT COUNT(*) FROM pages WHERE id_parent = YOUR_PAGE_ID OR (id = YOUR_PAGE_ID AND id_parent IS NOT NULL)
然后,我有一条简单的interface BannerProps {
type: typeof possibleBannerTypes[number];
data?: unknown
}
语句链,它们根据type参数返回不同的UI组件。
if/else if
将function test(bannerData: EmailBounceBannerProps | BannerProps) {
if (bannerData.type === 'anotherBanner') {
// do something
} else if (bannerData.type === 'emailBounce') {
console.log(bannerData.data.reason)
}
}
属性设置为特定值(type
)的对象具有我也想键入的data属性,以便可以在VS Code中使用类型检查和Intellisense。
emailBounce
但是,我似乎无法使其正常工作,打字稿似乎无法弄清何时填充interface EmailBounceBannerProps extends BannerProps{
type: 'emailBounce';
data: {
reason: string;
};
}
和type === 'emailBounce
属性。
我在TypeScript游乐场上创建了一个小片段来说明此问题:
我要做的就是让它通过无错误,同时获得基于data
的代码建议
我很确定自己之前已经成功完成了类似的工作,但是我无法弄清楚自己在做什么错。我也不确定这种做法或代码模式是什么,所以到目前为止,我在Google上搜索并没有获得任何成功的结果。
有人有解决方案,或者有更好的方法吗?
答案 0 :(得分:2)
第一个问题是possibleBannerTypes
将被扩展为string[]
,我们需要一个as const
来保持文字类型。
第二个问题是,由于您在分支BannerProps
上与bannerData.type === 'emailBounce'
进行了联合,因此您并没有真正缩小范围,因为bannerData
仍然可以是EmailBounceBannerProps
或{ {1}}。这意味着BannerProps
将是data
,而仅仅是unknown | { reason: string }
。
您需要一个默认案例,该案例要从unknown
属性中排除任何已知案例。您可以使用type
键入此默认接口的Exclude
并在联合中使用它代替type
:
BannerProps