如何用Zod实现查询字符串转指定字面量数字的输入验证?
解决方案
针对搜索查询的字符串输入场景,你可以通过「类型转换 + 管道验证」的方式实现需求,同时保证Schema推断出的类型与TypeScript的1 | -1完全兼容:
方法1:使用coerce自动转换 + 管道验证
这是最简洁的写法,z.coerce.number()会自动将输入的字符串转换为数字,再通过pipe传递给字面量联合类型验证:
import { z } from "zod"; const searchSchema = z.object({ x: z.coerce.number().pipe(z.union([z.literal(1), z.literal(-1)])) }); // 推断出的类型:{ x: 1 | -1 } type SearchInput = z.infer<typeof searchSchema>;
验证逻辑说明
- 若输入为
"1"或"-1",会被转换为数字1或-1,通过验证 - 若输入为其他字符串(如
"2"、"abc"),转换后的值不符合字面量要求,验证失败
方法2:显式transform转换 + 管道验证
如果你需要更精细的转换控制(比如指定进制),可以用transform手动转换字符串为数字,再走验证流程:
import { z } from "zod"; const searchSchema = z.object({ x: z.string() .transform(str => parseInt(str, 10)) // 显式按十进制转换 .pipe(z.union([z.literal(1), z.literal(-1)])) }); type SearchInput = z.infer<typeof searchSchema>; // { x: 1 | -1 }
优势
- 可以自定义转换逻辑(比如处理可能的空字符串、非数字字符等)
- 转换和验证步骤清晰,便于调试
类型兼容说明
通过pipe将转换后的结果传递给z.literal(1) | z.literal(-1),Zod会自动推断出最终类型为1 | -1,和你定义的TypeScript原生类型完全匹配,无需额外类型断言。
内容的提问来源于stack exchange,提问作者Alex
相关产品推荐
相关产品推荐

