You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于if子句的JSON Schema验证:按template值匹配parameters属性

问题:根据模板值动态验证parameters属性的JSON Schema编写

我需要为如下YAML结构编写JSON Schema验证:

stages:

  - template: template-a.yml
    parameters:
      a-param1: abc
      a-param2: xy

  - template: template-b.yml
    parameters:
      b-param1: df
      b-param2: yz

需求是根据template属性的值,让parameters对象拥有对应的不同属性。我尝试了如下Schema,但其中的if/then规则对对象属性不生效(仅当属性与template同层级时有效):

{
    "$schema": "http://json-schema.org/draft-07/schema#",
    "$ref": "#/definitions/azure-templates",
    "definitions": {
        "azure-templates": {
            "type": "object",
            "additionalProperties": false,
            "properties": {
                "stages": {
                    "type": "array",
                    "items": {
                        "anyOf": [
                            {
                                "$ref": "#/definitions/template-select"
                            }
                        ]
                    }
                }
            },
            "required": [
                "stages"
            ],
            "title": "azure-pipeline"
        },
        "template-params-a": {
            "if": {
                "properties": {
                    "template": {
                        "const": "template-a.yml"
                    }
                },
                "required": [
                    "template"
                ]
            },
            "then": {
                "properties": {
                    "parameters": {
                        "type": "object",
                        "additionalProperties": false,
                        "properties": {
                            "a-param1": {
                                "type": "string"
                            },
                            "a-param2": {
                                "type": "string"
                            }
                        }
                    }
                }
            }
        },
        "template-params-b": {
            "if": {
                "properties": {
                    "template": {
                        "const": "template-b.yml"
                    }
                },
                "required": [
                    "template"
                ]
            },
            "then": {
                "properties": {
                    "parameters": {
                        "type": "object",
                        "additionalProperties": false,
                        "properties": {
                            "b-param1": {
                                "type": "string"
                            },
                            "b-param2": {
                                "type": "string"
                            }
                        }
                    }
                }
            }
        },
        "template-select": {
            "type": "object",
            "additionalProperties": false,
            "properties": {
                "template": {
                    "enum": [
                        "template-a.yml",
                        "template-b.yml"
                    ]
                }
            },
            "allOf": [
                {
                    "$ref": "#/definitions/template-params-a",
                    "$ref": "#/definitions/template-params-b"
                }
            ],
            "required": [
                "template"
            ],
            "title": "Template"
        }
    }
}

修正后的Schema及说明

你的Schema有两个核心问题:

  1. template-select里的additionalProperties: false会直接拒绝parameters属性,因为初始properties里只定义了template,没有声明parameters的存在
  2. allOf数组里的对象重复使用$ref键,JSON Schema会忽略重复的键,最终只有最后一个$ref生效,导致template-params-a的规则完全没起作用

以下是修正后的Schema:

{
    "$schema": "http://json-schema.org/draft-07/schema#",
    "$ref": "#/definitions/azure-templates",
    "definitions": {
        "azure-templates": {
            "type": "object",
            "additionalProperties": false,
            "properties": {
                "stages": {
                    "type": "array",
                    "items": {
                        "$ref": "#/definitions/template-select"
                    }
                }
            },
            "required": ["stages"],
            "title": "azure-pipeline"
        },
        "template-a-params": {
            "type": "object",
            "additionalProperties": false,
            "properties": {
                "a-param1": {"type": "string"},
                "a-param2": {"type": "string"}
            },
            "required": ["a-param1", "a-param2"]
        },
        "template-b-params": {
            "type": "object",
            "additionalProperties": false,
            "properties": {
                "b-param1": {"type": "string"},
                "b-param2": {"type": "string"}
            },
            "required": ["b-param1", "b-param2"]
        },
        "template-select": {
            "type": "object",
            "additionalProperties": false,
            "properties": {
                "template": {
                    "enum": ["template-a.yml", "template-b.yml"]
                },
                "parameters": {}
            },
            "required": ["template"],
            "allOf": [
                {
                    "if": {"properties": {"template": {"const": "template-a.yml"}}},
                    "then": {"properties": {"parameters": {"$ref": "#/definitions/template-a-params"}}}
                },
                {
                    "if": {"properties": {"template": {"const": "template-b.yml"}}},
                    "then": {"properties": {"parameters": {"$ref": "#/definitions/template-b-params"}}}
                }
            ],
            "title": "Template"
        }
    }
}

关键修改点:

  • 在template-select的properties里先声明parameters为任意类型,避免被additionalProperties: false拒绝
  • 将if/then规则直接整合到allOf的数组项中,每个规则单独成为一个对象,确保所有规则都能生效
  • 把参数结构抽成独立的定义,让Schema更清晰
  • 给每个参数集合加上required,确保必填参数不缺失(如果不需要必填可以去掉)

内容的提问来源于stack exchange,提问作者Kai Goerlich

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.26 13:04:53