TypeScript中如何定义通用类型工具以抽象不同类型校验逻辑?
核心问题原因
你设想的语法不生效是因为 TypeScript 目前稳定版不支持原生高阶类型,即不能将泛型类型构造器本身作为另一个泛型的参数传入,直接写U<T>的调用形式不符合TS语法规范。
我们可以通过「类型映射表」的方式模拟高阶类型能力,实现通用的校验器抽象,完全可以覆盖你提到的所有场景:
实现方案
步骤1:定义校验器映射表
把所有你需要的校验逻辑都收敛到同一个接口中,接口的泛型参数为待校验的目标类型,键名为校验器的唯一标识,值为对应校验逻辑的返回类型:
type IsBoolean<T> = T extends boolean ? true : false; interface ValidatorMap<T> { // 基础宽类型校验 IsBoolean: IsBoolean<T>; IsString: T extends string ? true : false; IsNumber: T extends number ? true : false; // 特殊字面量校验 IsTrue: IsBoolean<T> extends true ? T extends true ? true : T extends false ? false : unknown : false; // 函数类型校验 IsFunction: T extends Function | (Function & {[key:string]:any}) ? true : false; // 可扩展任意自定义校验逻辑,比如校验带特定属性的函数 IsFunctionWithId: T extends Function & {id: string} ? true : false; }
步骤2:实现通用Validator类型
基于映射表实现通用的校验类型工具,泛型第一个参数为待校验类型,第二个参数为映射表中对应的校验器名称:
type Validator<T, K extends keyof ValidatorMap<any>> = ValidatorMap<T>[K];
步骤3:使用示例
// 校验boolean类型 type Test1 = Validator<boolean, 'IsBoolean'>; // 类型为 true type Test2 = Validator<string, 'IsBoolean'>; // 类型为 false // 校验true字面量 type Test3 = Validator<true, 'IsTrue'>; // 类型为 true type Test4 = Validator<false, 'IsTrue'>; // 类型为 false type Test5 = Validator<boolean, 'IsTrue'>; // 类型为 unknown type Test6 = Validator<number, 'IsTrue'>; // 类型为 false // 校验函数类型 type Test7 = Validator<() => void, 'IsFunction'>; // 类型为 true type Test8 = Validator<{id: '1'}, 'IsFunctionWithId'>; // 类型为 false
步骤4:配套运行时校验函数的通用类型
你也可以为配套的运行时校验函数定义通用类型,实现类型和运行时逻辑的统一收敛:
// 通用运行时校验函数类型 type ValidatorFunction<K extends keyof ValidatorMap<any>> = <T>(val: T) => Validator<T, K>; // 实现示例 const isBoolean: ValidatorFunction<'IsBoolean'> = (i) => { return (typeof i === 'boolean') as any; }; const isTrue: ValidatorFunction<'IsTrue'> = (i) => { return (i === true) as any; }; // 使用时自动关联类型校验 const a = isBoolean(true); // a的类型为 true const b = isBoolean('123'); // b的类型为 false
扩展说明
如果后续需要新增校验模式,只需要在ValidatorMap接口中新增对应的键值对即可,无需修改通用的Validator类型定义。
内容的提问来源于stack exchange,提问作者ken
相关产品推荐
相关产品推荐

