如何用Joi实现:属性A存在则B/C/D至少一个必须存在?
使用Joi实现「当属性a存在时,b/c/d至少一个必须存在」的校验规则
完全可以用Joi实现这个需求,核心是结合.when()条件判断和.or()多属性校验方法,以下是具体实现方案:
核心Schema实现
const Joi = require('joi'); // 定义校验schema const schema = Joi.object({ a: Joi.boolean(), // 根据实际需求调整a的类型,比如string/number等 b: Joi.boolean(), c: Joi.boolean(), d: Joi.boolean() }) // 当属性a存在时,触发后续校验规则 .when(Joi.object({ a: Joi.exist() }).unknown(), { then: Joi.object().or('b', 'c', 'd') });
关键逻辑说明
Joi.object({ a: Joi.exist() }).unknown():作为.when()的触发条件,意思是只要对象中存在a属性(无论值是什么),就执行then里的规则Joi.object().or('b', 'c', 'd'):强制要求对象中b、c、d至少有一个属性存在且有效(.or()默认会忽略undefined的属性,若需严格校验值不为undefined,可结合Joi.not(Joi.undefined()))
如果你的需求是当a为true时才触发校验(而非只要a存在),可将触发条件修改为:
.when(Joi.object({ a: Joi.valid(true) }).unknown(), { then: Joi.object().or('b', 'c', 'd') });
测试用例验证
对应你提供的测试对象,校验结果和原生JS逻辑完全一致:
const o1 = { a: true, b: undefined, c: true, d: undefined }; const o2 = { a: true, b: undefined, c: undefined, d: undefined }; const o3 = { a: undefined, b: true, c: undefined, d: undefined }; // 执行校验 const result1 = schema.validate(o1); const result2 = schema.validate(o2); const result3 = schema.validate(o3); console.log(result1.error); // undefined(校验通过) console.log(result2.error?.details[0].message); // "b"、"c"、"d"中至少一个是必需的 console.log(result3.error); // undefined(校验通过,a不存在时不触发规则)
补充说明
- 若需更复杂的属性类型校验,只需修改对应属性的Joi规则即可(比如把
Joi.boolean()改成Joi.string().required()) .or()方法支持传入任意数量的属性名,是处理「至少一个满足」场景的核心方法
内容的提问来源于stack exchange,提问作者BJ Rutledge
相关产品推荐
相关产品推荐

