如何在TypeScript中强制对象数组的属性值为非空字符串?
实现数组中非空字符串属性的TypeScript校验
原有单个对象的校验逻辑
先看单个对象的非空value属性校验实现:
type EnforceNonEmptyValue<TValueArg extends string> = { value: TValueArg extends '' ? never : TValueArg type: 'substringMatch' } function identity<TValueArg extends string>( object: EnforceNonEmptyValue<TValueArg> ) { return object } // 传入空字符串会触发错误 identity({value: '', type: 'substringMatch'}) // 错误提示:`Type 'string' is not assignable to type 'never'.ts(2322)` // 传入非空字符串正常运行 identity({value: 'works', type: 'substringMatch'})
这个实现通过泛型EnforceNonEmptyValue,将空字符串''对应的value类型映射为never,从而在传入空字符串时触发TypeScript类型错误,强制value为非空字符串。
扩展到数组的校验实现
要实现数组中每个对象的value都不能是空字符串,我们可以基于原有类型扩展出数组版本的校验函数:
// 复用原有非空值约束类型 type EnforceNonEmptyValue<TValueArg extends string> = { value: TValueArg extends '' ? never : TValueArg type: 'substringMatch' } // 数组校验函数 function identityArray<T extends readonly EnforceNonEmptyValue<string>[]>( arr: T ) { return arr } // 测试:包含空字符串的数组会报错 identityArray([ { type: 'substringMatch', value: 'np-payment', }, { type: 'substringMatch', value: '', // 此处触发错误:Type 'string' is not assignable to type 'never'.ts(2322) }, ]) // 全非空的数组正常运行 identityArray([ { type: 'substringMatch', value: 'np-payment', }, { type: 'substringMatch', value: 'valid-entry', }, ])
实现原理
- 通过泛型
T约束输入数组的每个元素都必须符合EnforceNonEmptyValue<string>类型; - 当数组中某个对象的
value为空字符串时,该对象的value类型会被解析为never,与string类型不兼容,从而触发TypeScript的类型错误提示; - 非空字符串的对象则会正常通过类型校验,因为
TValueArg会被推断为具体的非空字符串类型,不会映射到never。
内容的提问来源于stack exchange,提问作者Arihant
相关产品推荐
相关产品推荐

