一、什么是 dependentRequired 单向限制?
它的核心逻辑是:
**如果 A 字段存在,那么 B 字段必须同时存在;但反过来,B 字段存在时,A 字段可以不存在。**也就是我们常说的「单向依赖」。
二、结合示例拆解
{
"type": "object",
"properties": {
"creditCard": { "type": "string" },
"billingAddress": { "type": "string" }
},
"dependentRequired": {
"creditCard": ["billingAddress"]
}
}
规则解读
- 这行
"creditCard": ["billingAddress"]表示: 只要creditCard(信用卡号)字段出现了,billingAddress(账单地址)字段必须同时出现。 - 反过来,如果只有
billingAddress,没有creditCard,是完全合法的。
合法 / 非法场景对比
表格
| JSON 数据 | 校验结果 | 原因 |
|---|---|---|
{"creditCard": "123456", "billingAddress": "北京"} |
✅ 通过 | 依赖规则触发,两个字段都存在 |
{"billingAddress": "北京"} |
✅ 通过 | 只有被依赖字段,没有触发依赖规则 |
{} |
✅ 通过 | 两个字段都不存在,不触发规则 |
{"creditCard": "123456"} |
❌ 失败 | 触发了依赖规则,但缺少 billingAddress |
三、报错解析
报错信息:
json-schema.exceptions.ValidationError: 'loginUser' is a required property
Failed validating 'required' in schema['properties']['data']['items']:
{'type': 'object', 'required': ['id', 'loginUser'], ...}
这个报错是因为用了 required,而不是 dependentRequired:
- 写了
"required": ["id", "loginUser"],意思是:不管什么情况,id和loginUser两个字段都必须存在,这是强制的,和依赖无关。 - 如果你想改成「只有当某个字段存在时,
loginUser才必须存在」,就要用dependentRequired,而不是直接写required。
四、完整可运行示例(带单向依赖)
from jsonschema import validate
def test_dependent_required():
# 1. 合法场景:creditCard 和 billingAddress 同时存在
valid1 = {
"creditCard": "4111-1111-1111-1111",
"billingAddress": "北京市朝阳区"
}
# 2. 合法场景:只有 billingAddress,没有 creditCard
valid2 = {
"billingAddress": "上海市浦东新区"
}
# 3. 合法场景:两个字段都不存在
valid3 = {}
# 4. 非法场景:只有 creditCard,没有 billingAddress
invalid = {
"creditCard": "4111-1111-1111"
}
# 带单向依赖的 Schema
schema = {
"type": "object",
"properties": {
"creditCard": {"type": "string"},
"billingAddress": {"type": "string"}
},
"dependentRequired": {
"creditCard": ["billingAddress"]
}
}
# 校验合法数据
validate(instance=valid1, schema=schema)
validate(instance=valid2, schema=schema)
validate(instance=valid3, schema=schema)
print("✅ 所有合法场景校验通过")
# 校验非法数据(会报错)
# validate(instance=invalid, schema=schema)
五、和 required 的核心区别
| 关键字 | 作用 | 适用场景 |
|---|---|---|
required |
强制字段必须存在,和其他字段无关 | 无论什么情况,字段都不能少 |
dependentRequired |
字段存在时,其他字段必须同时存在 | 字段之间有依赖关系,比如 "有信用卡号就必须有账单地址" |
💡 小技巧:
- 一个字段可以依赖多个字段,比如
"age": ["height", "gender"],表示有age时,height和gender都必须存在。 - 多个字段也可以依赖同一个字段,比如
"a": ["c"], "b": ["c"],表示有a或b时,c必须存在。