有没有更简单的方法将键与映射对象中的值相关联?

时间:2019-12-05 17:07:28

标签: typescript

我有一个对象,其中值直接与键相关,这意味着这是有效的:

const x = {
  test(action: { type: 'test', payload: unknown }){ /*...*/ }
}

但这是无效的:

const x = {
  test(action: { type: 'notTest', payload: unknown }){ /*...*/ }
}

我正在通过创建一个从不指定或直接使用但通过第二个映射进行验证的隐式泛型来实现自己的目标。

所以我的解决方案如下:

type Action<T> = {type: T};

interface ActionListenerMiddlewareListener<A extends Action<any>> {
  (action: A): void
}

export type CaseListeners = Record<
  string,
  ActionListenerMiddlewareListener<any>
>

export type CaseListenersCheck<Listeners extends CaseListeners> = {
  [T in keyof Listeners]: Listeners[T] extends ActionListenerMiddlewareListener<
    infer A
  >
    ? A extends { type: T }
      ? Listeners[T]
      : /* 
      Type is not matching the object key. 
      Return ActionListenerMiddlewareListener<Action<T>> to hint in the resulting error message that this is wrong.
      */ ActionListenerMiddlewareListener<
          Action<T>
        >
    : never
}

export type ValidCaseListeners<Listeners extends CaseListeners> = Listeners &
  CaseListenersCheck<Listeners>

export function createActionListenerMiddleware<Listeners extends CaseListeners>(
  cases: ValidCaseListeners<Listeners>
): any {
    // ...

}

但是,当然,我希望使用一种类型来检查这种有效性,而不是使用我现在拥有的这种隐式泛型的现场限制结构。

有没有更简单的方式编写此代码?

0 个答案:

没有答案