У меня есть следующая схема. Я реализовал это как мог, но он все еще не работает так, как я хочу.
{
"$schema": "http://json-schema.org/draft-07/schema#",
"type": "object",
"title": "Ordering pizza",
"propertyNames": {
"enum": [
"q-who-did-you-order-from",
"q-did-they-accept-your-order",
"q-how-much-was-the-bill",
"q-why-didnt-they-accept"
]
},
"properties": {
"q-who-did-you-order-from": {
"type": "string",
"title": "Who have you ordered pizza from?",
"maxLength": 50,
"errorMessages": {
"required": "Enter who you ordered from",
"maxLength":
"Who you ordered from must be 50 characters or less"
}
},
"q-did-they-accept-your-order": {
"title": "Have they accepted your order?",
"type": "boolean",
"errorMessages": {
"required":
"Select yes if they have accepted your order"
}
},
"q-how-much-was-the-bill": {
"type": "string",
"title": "How much was the bill?",
"maxLength": 50,
"errorMessages": {
"required": "Enter an amount",
"maxLength": "Amount must be 50 characters or less"
}
},
"q-why-didnt-they-accept": {
"type": "string",
"title": "Why wasnt your order accepted?",
"description":
"If you do not know you can say so.",
"maxLength": 50,
"errorMessages": {
"required": "Enter a reason",
"maxLength": "Reason must be 50 characters or less"
}
}
},
"required": ["q-who-did-you-order-from", "q-did-they-accept-your-order"],
"allOf": [
{
"$ref": "#/definitions/if-false-then-q-why-didnt-they-accept-is-required"
},
{
"$ref": "#/definitions/if-true-then-q-how-much-was-the-bill-is-required"
}
],
"definitions": {
"if-false-then-q-why-didnt-they-accept-is-required": {
"if": {
"properties": {
"q-did-they-accept-your-order": {
"const": false
}
}
},
"then": {
"required": ["q-why-didnt-they-accept"],
"propertyNames": {
"enum": [
"q-who-did-you-order-from",
"q-did-they-accept-your-order",
"q-why-didnt-they-accept"
]
}
}
},
"if-true-then-q-how-much-was-the-bill-is-required": {
"if": {
"properties": {
"q-did-they-accept-your-order": {
"const": true
}
}
},
"then": {
"required": ["q-how-much-was-the-bill"],
"propertyNames": {
"enum": [
"q-who-did-you-order-from",
"q-did-they-accept-your-order",
"q-how-much-was-the-bill"
]
}
}
}
}
}
Ожидается, что пользователь введет значение для q-who-did-you-order-from и q-did-они-accept-your-order, а затем только один из оставшихся двух вопросов на основе своего ответа для Q-сделал-они-принять-ваш заказ.
Таким образом, следующие входные данные должны проверяться:
{
"q-did-you-order-from": "Pizza hut",
"q-did-they-accept-your-order": "true",
"q-how-much-was-the-bill": "20"
}
{
"q-did-you-order-from": "Pizza hut",
"q-did-they-accept-your-order": "false",
"q-why-didn't-they-accept": "Incorrect card details"
}
Точно так же я ожидаю, что следующие входные данные не пройдут проверку и выдадут «обязательную» ошибку для поля, содержащего пустую строку. Первый должен выдать ошибку, потому что q-Why-not-они-accept пуст:
{
"q-did-you-order-from": "Pizza hut",
"q-did-they-accept-your-order": "false",
"q-why-didn't-they-accept": ""
}
И этот должен выдать ошибку, потому что q-сколько-было-было-счет пусто.
{
"q-did-you-order-from": "Pizza hut",
"q-did-they-accept-your-order": "true",
"q-how-much-was-the-bill": ""
}
И это так! Это работает как ожидалось. Однако мы обнаружили ошибку, которая возникает из-за того, что пользователь не вводил ответ на q-did-они-accept-your-order. Ответы на эти вопросы отправляются через браузер при отправке формы. В браузере логический вопрос представлен в виде переключателей да / нет. В результате, когда пользователь не проверяет радио, но пытается отправить форму, ответ на радио полностью опускается. Отправленный объект данных выглядит так:
{
"q-did-you-order-from": "Pizza hut",
"q-how-much-was-the-bill": "",
"q-why-didn't-they-accept": "",
}
Мой ожидаемый результат здесь:
AJV выдает только одну «обязательную» ошибку для q-did-они-принимают-ваш-заказ. Он не должен выдавать «требуемую» ошибку для чего-либо еще, так как и q-сколько-сколько-было-счета-фактуры, и q-почему-не-они-принимаемые не требуются, если только соответствующее значение для q-did -принято-ваш заказ выбран.
Мой фактический результат:
AJV Выдает ошибку для всех трех пустых входов.
Итак, мой вопрос: как мне заставить AJV проверить эту схему и ТОЛЬКО q-did-they-accept-accept-your-order выдать требуемую ошибку, когда на вопрос нет ответа.
EDIT:
Выход AJV выглядит следующим образом:
[
{
"keyword": "required",
"dataPath": "",
"schemaPath": "#/required",
"params": {
"missingProperty": "q-did-they-accept-your-order"
},
"message": "should have required property 'q-did-they-accept-your-order'"
},
{
"keyword": "required",
"dataPath": "",
"schemaPath": "#/definitions/if-false-then-q-why-didnt-they-accept-is-required",
"params": {
"missingProperty": "q-why-didnt-they-accept"
},
"message": "should have required property 'q-why-didnt-they-accept'"
},
{
"keyword": "if",
"dataPath": "",
"schemaPath": "#/definitions/if-false-then-q-why-didnt-they-accept-is-required/if",
"params": {
"failingKeyword": "then"
},
"message": "should match \"then\" schema"
},
{
"keyword": "required",
"dataPath": "",
"schemaPath": "#/definitions/if-true-then-q-how-much-was-the-bill-is-required/then/required",
"params": {
"missingProperty": "q-how-much-was-the-bill"
},
"message": "should have required property 'q-how-much-was-the-bill'"
},
{
"keyword": "if",
"dataPath": "",
"schemaPath": "#/definitions/if-true-then-q-how-much-was-the-bill-is-required/if",
"params": {
"failingKeyword": "then"
},
"message": "should match \"then\" schema"
}
]