打字稿检查是否类型 A === 类型 B |C型 [英] Typescript check if type A === type B | type C

查看:32
本文介绍了打字稿检查是否类型 A === 类型 B |C型的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在一个文件中,我有这样的内容:

In one file I have something like this:

export const _all = {
  a: '',
  b: '',
  c: '',
  d: '',
  e: '',
  f: '',
}
type AllKeysType = typeof _all;
export type AllKey = keyof AllKeysType;

在另一个文件中,我有这样的东西:

In another file I have something like this:

export const _keep = {
  a: '',
  b: '',
  d: '',
  e: '',
}
type KeepKeysType = typeof _keep;
export type KeepKey = keyof KeepKeysType;

export const _ignore = {
  c: '',
  f: '',
}
type IgnoreKeysType = typeof _ignore;
export type IgnoreKey = keyof IgnoreKeysType;

我如何使用 Typescript 来断言 _all 中定义的键总是等于 _keep_ignore 的并集.换句话说,AllKey 应该总是等于 KeepKey |IgnoreKey.

How can I use Typescript to assert that the keys defined in _all ALWAYS is equal to the union of _keep and _ignore. In other words, AllKey should always be equal to KeepKey | IgnoreKey.

如果开发人员通过添加新值(比如 z)更新 _all 但忘记添加 z,我希望 Typescript 编译器给我一个错误_keep_ignore 中.

I want the Typescript compiler to give me an error if a developer updates _all by adding in a new value (say z) but forgets to add z into either _keep or _ignore.

推荐答案

这可以通过定义一个接受两种类型并在输入类型相等或 时解析为 true 的条件类型来实现false 否则.然后编写一些代码,当该类型不是 true 时会抛出编译错误.

This is possible by defining a conditional type that accepts two types and resolves to true when the input types are equal or false otherwise. Then write some code that will throw a compile error when that type is not true.

当任何一种类型更改时,您都会收到编译错误,这将确保您记住更新不同步的任何类型.当您希望收到有关不同库中类型更改的通知时,这尤其有用.

When either of the types change you'll get a compile error which will ensure you remember to update whichever type is out of sync. This is especially useful when you want to be notified about changes to a type in a different library.

例如:

type IsExact<T, U> = [T] extends [U] ? [U] extends [T] ? true : false : false;
function assert<T extends true | false>(expectTrue: T) {}

// this will throw a compile error when the two types get out of sync
assert<IsExact<AllKey, KeepKey | IgnoreKey>>(true);

更健壮的代码有点长(例如处理 any 类型),但它已汇总在我的库中 此处.

More robust code is a little longer (ex. handling the any type), but it's rolled up in my library here.

import { assert, IsExact } from "conditional-type-checks";

// define or import AllKey, KeepKey, IgnoreKey

assert<IsExact<AllKey, KeepKey | IgnoreKey>>(true);

另一种选择

另一种不太好的方法是创建两种类型的两个对象并将它们分配给彼此.

Another not so nice way of doing this is to create two objects of the two types and assign them to each other.

() => {
  let allKeys: AllKey;
  let otherKeys: KeepKey | IgnoreKey;

  // do this in lambdas to prevent the first assignment from changing
  // the type of the variable being assigned to
  () => allKeys = otherKeys;
  () => otherKeys = allKeys;
};

这篇关于打字稿检查是否类型 A === 类型 B |C型的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆