最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Typescript make one parameter type depend on the other parameter - Stack Overflow

programmeradmin4浏览0评论

Say I have

interface Action<T> {
    assignAction(key: keyof T, value: any): void;
}

Say T is of type

{
    users: User[];
    accounts: Account[];
}

Now, when calling assignAction, let's say I want to pass users. So this action is false because types don't match:

assignAction('users', accounts)

I don't know how to validate value, since its type depends on what you choose for key.

Say I have

interface Action<T> {
    assignAction(key: keyof T, value: any): void;
}

Say T is of type

{
    users: User[];
    accounts: Account[];
}

Now, when calling assignAction, let's say I want to pass users. So this action is false because types don't match:

assignAction('users', accounts)

I don't know how to validate value, since its type depends on what you choose for key.

Share Improve this question edited Jan 13, 2021 at 11:40 Robert Koritnik 105k56 gold badges284 silver badges413 bronze badges asked Jan 12, 2018 at 18:49 KoushaKousha 36.2k59 gold badges186 silver badges313 bronze badges 1
  • 1 createAction should be assignAction? – tokland Commented Jan 31, 2019 at 13:53
Add a comment  | 

2 Answers 2

Reset to default 21

You should be able to add a generic to the assignAction function to help describe this relationship.

interface Action<T> {
    assignAction<K extends keyof T>(key: K, value: T[K]): void;
}

Then once your Action instance is given a generic type it knows how to associate the relationship between key and value when you call assignAction

interface TypeA {
    objectIdA: string
}

interface TypeB {
    objectIdB: string
}

interface TypeC {
    objectIdC: string
}

enum Param1 {
    TypeA = "TypeA",
    TypeBC = "TypeBC"
}



type INamespaceKeyMap =
    & Record<Param1.TypeA, TypeA>
    & Record<Param1.TypeBC, TypeB | TypeC>;

type INamespaceKeys<T extends Param1.TypeA | Param1.TypeBC> = INamespaceKeyMap[T];

function test<NS extends Param1, Key extends INamespaceKeys<NS>>(namespace: NS, key: Key) {
    console.log("Called");
}

const objectA = {
    objectIdA: "test"
} as TypeA;

const objectB = {
    objectIdB: "test"
} as TypeB;

const objectC = {
    objectIdC: "test"
} as TypeC;

test(Param1.TypeA, objectB) // not allowed
test(Param1.TypeA, objectA)
test(Param1.TypeBC, objectA) // not allowed
test(Param1.TypeBC, objectB)
test(Param1.TypeBC, objectC)

发布评论

评论列表(0)

  1. 暂无评论