#json #jsonschema
#json #jsonschema
Вопрос:
Я хотел бы иметь возможность управлять массивом «объектов» в формате json, где каждый объект имеет тип и свойства, и возникает ошибка схемы, если в объекте отсутствует обязательное свойство.
Это моя попытка сделать это (не включая часть массива), объявляя два типа объектов и говоря, что объект в json может быть любого из этих типов:
{
'definitions':
{
'typeone':
{
'type': 'object',
'properties':
{
'xtype': {'type':'string', 'const':'typeone'},
'num' : {'type':'number'}
},
'required':['xtype', 'num'],
'additionalProperties':false
},
'typetwo':
{
'type': 'object',
'properties':
{
'xtype': {'type':'string', 'const':'typetwo'},
'str' : {'type':'string'}
},
'required':['xtype', 'str'],
'additionalProperties':false
}
},
'anyOf':
[
{ '$ref': '#/definitions/typeone' },
{ '$ref': '#/definitions/typetwo' },
]
}
Однако, если я передам ему json, который завершится неудачей, потому что в таком объекте отсутствует обязательное свойство:
{
'xtype': 'typeone'
}
… это ошибка с JSON does not match any schemas from 'anyOf'.
— я вижу, причина в том, что он не знает, чтобы попытаться сопоставить xtype, вместо этого он просто считает xtype ‘typeone’ недействительным и смотрит на других.
Есть ли лучший способ сделать anyOf
это, который будет жестко соответствовать на основе одного значения свойства (например, ‘switch’), а затем выдавать ошибки об отсутствии других обязательных свойств для этого типа объекта?
Комментарии:
1. Нет, но есть стандартизированный вывод из проекта схемы JSON 2019-09, который затем можно использовать для создания сообщений об ошибках. Извините.
Ответ №1:
Это становится намного более подробным, но вы можете использовать if
/ then
для переключения проверки на основе свойства «xtype».
{
"$schema": "http://json-schema.org/draft-07/schema#",
"allOf": [
{
"if": {
"type": "object",
"properties": {
"xtype": { "const": "typeone" }
},
"required": ["xtype"]
},
"then": { "$ref": "#/definitions/typeone" }
},
{
"if": {
"type": "object",
"properties": {
"xtype": { "const": "typetwo" }
},
"required": ["xtype"]
},
"then": { "$ref": "#/definitions/typetwo" }
}
],
"definitions": {
"typeone": {
"type": "object",
"properties": {
"xtype": {},
"num": { "type": "number" }
},
"required": ["num"],
"additionalProperties": false
},
"typetwo": {
"type": "object",
"properties": {
"xtype": {},
"str": { "type": "string" }
},
"required": ["str"],
"additionalProperties": false
}
}
}
С небольшим изменением модели вы могли dependencies
бы получить гораздо более простую и чистую схему. Вместо свойства «xtytpe» у вас может быть свойство, соответствующее имени типа. Например, { "typeone": true }
.
{
"$schema": "http://json-schema.org/draft-07/schema#",
"type": "object",
"dependencies": {
"typeone": {
"type": "object",
"properties": {
"typeone": {},
"num": { "type": "number" }
},
"required": ["num"],
"additionalProperties": false
},
"typetwo": {
"type": "object",
"properties": {
"typetwo": {},
"str": { "type": "string" }
},
"required": ["str"],
"additionalProperties": false
}
}
}
Комментарии:
1. Спасибо за эту идею, о которой я не думал