JSON模式:为什么“常量”不能以与单值“枚举”相同的方式进行验证?

Jer*_*son 2 json jsonschema

我有一个对象,提供一种资产版本的审核日志。它的几个属性(versionSource.metadataversionSource.files)是应根据两个架构之一验证的对象,具体取决于其架构之一的值。我开始在子方案中使用一个常量(在中oneOf,但那是说所有子方案都已验证(因此打破了oneOf多个已验证的方案。不过,将其更改为单值枚举是可行的)。

为什么验证有所不同?

这是原始架构:

{
   "$id": "https://example.com/schemas/asset-version.json",
   "title": "Audit log of asset versions",
   "$schema": "http://json-schema.org/draft-07/schema",

   "type": "object",
   "required": [
      "assetID",
      "version",
      "versionSource"
   ],

   "properties": {
      "assetID": {
         "type": "string"
      },
      "version": {
         "type": "integer",
         "minimum": 1
      },
      "versionSource": {
         "type": "object",
         "properties": {
            "metadata": {
               "type": "object",
               "oneOf": [
                  {
                     "properties": {
                        "sourceType": { "constant": "client" }
                     }
                  },
                  {
                     "$ref": "#/definitions/version-source-previous-version"
                  }
               ]
            },
            "files": {
               "type": "object",
               "oneOf": [
                  {
                     "properties": {
                        "sourceType": { "constant": "upload" },
                        "sourceID": {
                           "type": "string"
                        }
                     }
                  },
                  {
                     "$ref": "#/definitions/version-source-previous-version"
                  }
               ]
            }
         }
      }
   },

   "definitions": {
      "version-source-previous-version": {
         "properties": {
            "sourceType": { "constant": "previous-version" },
            "sourceID": {
               "type": "integer",
               "minimum": 1
            }
         }
      }
   }
}
Run Code Online (Sandbox Code Playgroud)

这是一个示例文档:

{
   "assetID": "0150a186-068d-43e7-bb8b-0a389b572379",
   "version": 1,
   "versionSource": {
      "metadata": {
         "sourceType": "client"
      },
      "files": {
         "sourceType": "upload",
         "sourceID": "54ae67b0-3e42-464a-a93f-3143b0f078fc"
      }
   },
   "created": "2018-09-01T00:00:00.00Z",
   "lastModified": "2018-09-02T12:10:00.00Z",
   "deleted": "2018-09-02T12:10:00.00Z"
}
Run Code Online (Sandbox Code Playgroud)

还有一个:

{
   "assetID": "0150a186-068d-43e7-bb8b-0a389b572379",
   "version": 2,
   "versionSource": {
      "metadata": {
         "sourceType": "previous-version",
         "sourceID": 1
      },
      "files": {
         "sourceType": "previous-version",
         "sourceID": 1
      }
   },
   "created": "2018-09-01T00:00:00.00Z",
   "lastModified": "2018-09-02T12:10:00.00Z",
   "deleted": "2018-09-02T12:10:00.00Z"
}
Run Code Online (Sandbox Code Playgroud)

这是我得到的错误:

消息:JSON对于来自“ oneOf”的多个模式有效。有效架构索引:0、1。架构路径:https//example.com/schemas/asset-version.json#/properties/versionSource/properties/metadata/oneOf

由于sourceType在中的两个架构中都是常量oneOf,因此我真的不确定我的对象如何针对两个架构都有效。

但是,将架构更改为以下内容是可行的:

{
   "$id": "https://example.com/schemas/asset-version.json",
   "title": "Audit log of asset versions",
   "$schema": "http://json-schema.org/draft-07/schema",

   "type": "object",
   "required": [
      "assetID",
      "version",
      "versionSource"
   ],

   "properties": {
      "assetID": {
         "type": "string"
      },
      "version": {
         "type": "integer",
         "minimum": 1
      },
      "versionSource": {
         "type": "object",
         "properties": {
            "metadata": {
               "type": "object",
               "oneOf": [
                  {
                     "properties": {
                        "sourceType": { "enum": [ "client" ] }
                     }
                  },
                  {
                     "$ref": "#/definitions/version-source-previous-version"
                  }
               ]
            },
            "files": {
               "type": "object",
               "oneOf": [
                  {
                     "properties": {
                        "sourceType": { "enum": [ "upload" ] },
                        "sourceID": {
                           "type": "string"
                        }
                     }
                  },
                  {
                     "$ref": "#/definitions/version-source-previous-version"
                  }
               ]
            }
         }
      }
   },

   "definitions": {
      "version-source-previous-version": {
         "properties": {
            "sourceType": { "enum": [ "previous-version" ] },
            "sourceID": {
               "type": "integer",
               "minimum": 1
            }
         }
      }
   }
}
Run Code Online (Sandbox Code Playgroud)

我想念什么?

and*_*abs 10

根据草案7

应该注意的是,const 只是具有单个元素的枚举的语法糖,因此以下内容是等效的:

{ "const": "United States of America" }

{ "enum": [ "United States of America" ] }
Run Code Online (Sandbox Code Playgroud)

有些人可能会发现在某些渲染表单解决方案中使用时提供default密钥很有用,以选择单个选项。


Jer*_*son 5

这是我自己的错字... constant应该是const。:facepalm: