简体   繁体   English

打字稿:属性的类型依赖于同一对象中的另一个属性

[英]Typescript: Type of a property dependent on another property within the same object

I have a TypeScript interface with two properties ( type:string and args:object ).我有一个带有两个属性的 TypeScript 接口( type:stringargs:object )。 The args may have different properties depending on the type . args可能具有不同的属性,具体取决于type What type definition to I need to apply to args so the compiler/autocomplete will know which properties are allowed for args ?我需要对args应用什么类型定义,以便编译器/自动完成将知道args允许哪些属性?

This is somewhat similar to how I use Actions in Redux, which do have a type and a payload and in my reducer the compiler knows by the switch-statement what the payload contains.这有点类似于我在 Redux 中使用 Actions 的方式,它有一个type和一个payload ,在我的减速器中,编译器通过 switch 语句知道有效负载包含什么。 But I can't get this to work with my object.但我不能让它与我的对象一起工作。 I have read an excellent article here https://artsy.github.io/blog/2018/11/21/conditional-types-in-typescript/ but this describes the problem for a method with two args which depend on one another but not how to get this working for two properties within the same object.我在这里阅读了一篇很棒的文章https://artsy.github.io/blog/2018/11/21/conditional-types-in-typescript/但这描述了具有两个相互依赖的 args 的方法的问题,但是不是如何让这对同一对象中的两个属性起作用。

export interface IObject {
  type: ObjectType
  parameters: ObjectParameters
}
export type ObjectType = "check" | "counter"
export interface IParametersCheck {
  checked: boolean
}
export interface IParametersCounter {
  max: number
  min: number
  step: number
}
export type ObjectParameters = IParametersCheck | IParametersCounter

If I have an IObject and set the type to "check" the compiler/autocomplete should offer the properties for IParametersCheck .如果我有一个IObject并将类型设置为“检查”,编译器/自动完成应该提供IParametersCheck的属性。

I think what you are actually looking for is a discriminated union.我认为您实际上正在寻找的是一个受歧视的工会。 IObject should itself be a union: IObject本身应该是一个联合:

export type IObject = {
    type: "checked"
    parameters: IParametersCheck
} | {
    type: "counter"
    parameters: IParametersCounter
}
export type ObjectType = IObject['type'] //// in case you need this union
export type ObjectParameters = IObject['parameters']  //// in case you need this union

export interface IParametersCheck {
    checked: boolean
}
export interface IParametersCounter {
    max: number
    min: number
    step: number
}

You could also do it with conditional types but I think the union solution works better :你也可以用条件类型来做,但我认为联合解决方案效果更好:

export interface IObject<T extends ObjectType> {
    type: T
    parameters: T extends 'checked' ? IParametersCheck: IParametersCounter
}

Or with a mapping interface:或者使用映射接口:

export interface IObject<T extends ObjectType> {
    type: T
    parameters: ParameterMap[T]
}
type ParameterMap ={
    'checked': IParametersCheck
    'counter': IParametersCounter
}

export type ObjectType = keyof ParameterMap

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 Typescript 接口 - 使一个属性的类型依赖于另一个属性的类型 - Typescript Interface - make type of one property dependent of type of another property Typescript - 如何将部分类型分配给另一个 object 的相同类型的属性? - Typescript - How to assign Partial type to the property of same type of another object? 我可以使对象属性类型依赖于另一种属性类型吗? - Can I make an object property type dependent of another property type? 更改 object 中的特定属性会更改相同类型的另一个 object 中的相同属性 Typescript - Changing a specific property inside an object changes that same property in another object of the same type Typescript TypeScript:一个接口属性依赖于另一个 - TypeScript: an interface property dependent on another TypeScript 类型取决于属性名称? - TypeScript type dependent on property name? 将 object 属性值传递给 Typescript Angular 中 object 中的另一个属性 - Pass object property value to another property within that object in Typescript Angular 在 typescript 中声明 object 中的所有属性相同类型? - declare all property in object the same type in typescript? Typescript:相同object的其他属性参考属性类型 - Typescript: Reference type of property by other property of same object 打字稿是对象属性的类型 - Typescript is Type for object property
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM