如何定义具有可变必填属性的JSON Schema(draft 2019-09)
符合JSON Schema Draft 2019-09的对象属性约束定义
需求说明
需要定义一个符合Draft 2019-09标准的JSON Schema,约束包含amount、productId、invoiceId、jwt四个属性的对象,规则如下:
amount、productId、invoiceId三者不能两两或三者同时存在invoiceId存在时必须伴随jwtjwt可单独存在,或与amount/productId其中之一共存- 对象至少包含上述属性中的一个,且满足所有规则
原方案问题分析
你之前的Schema存在几个问题:
oneOf数组未包含{"required": ["jwt"]},导致jwt单独存在时无法通过验证- 若直接添加
{"required": ["jwt"]}到oneOf,invoiceId与jwt共存的场景会同时满足两个required分支,违反oneOf"仅满足一个分支"的要求,导致验证失败 - 拼写错误:
dependantRequried应为标准的dependentRequired
正确的Schema实现
以下是满足所有需求的Schema:
{ "$schema": "https://json-schema.org/draft/2019-09/schema", "type": "object", "properties": { "amount": {"type": "number"}, "productId": {"type": "string"}, "invoiceId": {"type": "string"}, "jwt": {"type": "string"} }, "dependentRequired": { "invoiceId": ["jwt"] }, "anyOf": [ {"required": ["amount"]}, {"required": ["productId"]}, {"required": ["invoiceId"]}, {"required": ["jwt"]} ], "not": [ { "required": ["amount", "productId"] }, { "required": ["amount", "invoiceId"] }, { "required": ["productId", "invoiceId"] }, { "required": ["amount", "productId", "invoiceId"] } ] }
逻辑说明
dependentRequired:确保invoiceId存在时必须有jwt,直接拦截{"invoiceId": "inv-1"}这类非法数据anyOf:覆盖所有合法的核心属性存在情况,只要满足其中一个required规则即可(额外携带jwt不会影响验证通过)not数组:明确排除所有非法的属性组合,包括amount与productId共存、amount与invoiceId共存、productId与invoiceId共存,以及三者同时存在的情况
验证结果匹配
按照你的预期,以下场景验证结果完全符合要求:
| JSON示例 | 是否有效 |
|---|---|
{"amount": 1} | ✅ 是 |
{"amount": 1, "jwt": "jwt-test"} | ✅ 是 |
{"productId": "prod-1"} | ✅ 是 |
{"productId": "prod-1", "jwt": "jwt-test"} | ✅ 是 |
{"invoiceId": "inv-1", "jwt": "jwt-test"} | ✅ 是 |
{"jwt": "jwt-test"} | ✅ 是 |
{"invoiceId": "inv-1"} | ❌ 否 |
{"amount": 1, "productId": "prod-1"} | ❌ 否 |
{"amount": 1, "productId": "prod-1", "jwt": "jwt-test"} | ❌ 否 |
内容的提问来源于stack exchange,提问作者Matthew Sanford
相关产品推荐
相关产品推荐

