2
votes

Iam trying to define an optional condition using json schema conditional statement (Using draft 7)

I have a json response like this.

[{
    "views": [{
            "name": "RSO Roster",
            "displayOrder": 5,
            "groups": [{
                    "type": "scrollable",
                    "displayOrder": 1,
                    "auditType": "player-pregame_roster",
                    "tiles": [{
                            "context": "event",
                            "dataStamp": 1535184247,
                            "tile_type": "person"
                        }, {
                            "context": "event",
                            "errorCode": 2, 
                            "errorText": "seloger",                                 
                            "tile_type": "person"
                        }
                    ]
                }
            ]
        },
        {
            "name": "Leaders",
            "displayOrder": 1,
            "groups": [{
                    "type": "static",
                    "displayOrder": 1,                      
                    "tiles": [{
                            "context": "event",
                            "dataStamp": 1535184247,
                            "eventId":123
                            "tile_type": "static"
                        }
                    ]
                }
            ]
        }

    ]
}]

In this response if the tile object contains the key errorCode the required field must be errorText and errorCode keys.Like wise if the tile object doessnot contains any "errorCode" or "errorText" key then the tile item contains the required field "dataStamp".

To validate the above condition i have defined a schema like below.But it is not working.Whats wrong with my schema .

 {
    "$schema": "http://json-schema.org/draft-07/schema#",
    "type": "array",
    "items": {
        "type": "object",
        "properties": {
            "views": {
                "$id": "views",
                "type": "array",
                "items": {
                    "$id": "views/items",
                    "type": "object",
                    "properties": {
                        "groups": {
                            "$id": "views/groups",
                            "type": "array",
                            "items": {
                                "$id": "views/groups/items",
                                "type": "object",
                                "properties": {
                                    "tiles": {
                                        "$id": "views/groups/tiles",
                                        "type": "array",
                                        "items": {
                                            "$id": "views/groups/tiles/items",
                                            "type": "object",
                                            "properties": {
                                                "dataStamp": {
                                                    "$id": "views/groups/tiles/dataStamp",
                                                    "type": "integer"
                                                },
                                                "tile_type": {
                                                    "$id": "views/groups/tiles/tile_type",
                                                    "type": "string"
                                                },
                                                "errorCode": {
                                                    "type": "integer",
                                                    "enum": [
                                                        2, 10
                                                    ]
                                                },
                                                "errorText": {
                                                    "type": "string",
                                                    "enum": [
                                                        "seloger", "france24"
                                                    ]
                                                }
                                            },
                                            "if": {
                                                "properties": {
                                                    "tile_type": {
                                                        "enum": ["person"]
                                                    },
                                                    "errorCode": {
                                                        "enum": [2, 10]
                                                    }

                                                },
                                                "required": ["errorCode", "errorText"]
                                            }

                                        }
                                    }
                                },
                                "required": [
                                    "type",
                                    "tiles"
                                ]
                            }
                        }
                    },
                    "required": [
                        "groups"
                    ]
                }
            }
        },
        "required": [
            "views"
        ]
    }
}
1

1 Answers

1
votes

The if statement is missing required in properties:

                                        "if": {
                                            "properties": {
                                                "tile_type": {
                                                    "enum": ["person"]
                                                },
                                                "errorCode": {
                                                    "enum": [2, 10]
                                                },
                                                "required": ["errorCode"]
                                            }
                                        },

If there is no required the value of property is validated only if the property is set. So original if schema would pass any object without tile_type and errorCode.

https://stackoverflow.com/a/51034071/329463 might give you some inspiration on building exclusive properties clusters.

EDIT: modified full schema

{
    "$schema": "http://json-schema.org/draft-07/schema#",
    "type": "array",
    "items": {
        "type": "object",
        "properties": {
            "views": {
                "$id": "views",
                "type": "array",
                "items": {
                    "$id": "views/items",
                    "type": "object",
                    "properties": {
                        "groups": {
                            "$id": "views/groups",
                            "type": "array",
                            "items": {
                                "$id": "views/groups/items",
                                "type": "object",
                                "properties": {
                                    "tiles": {
                                        "$id": "views/groups/tiles",
                                        "type": "array",
                                        "items": {
                                            "$id": "views/groups/tiles/items",
                                            "type": "object",
                                            "properties": {                                                                                                                                             
                                                "dataStamp": {
                                                    "$id": "views/groups/tiles/dataStamp",
                                                    "type": "integer"
                                                },                                              
                                                "tile_type": {
                                                    "$id": "views/groups/tiles/tile_type",
                                                    "type": "string"
                                                },
                                                "errorCode": {
                                                    "type": "integer",
                                                    "enum": [
                                                        2, 10
                                                    ]
                                                },
                                                "errorText": {
                                                    "type": "string",
                                                    "enum": [
                                                        "seloger", "france24"
                                                    ]
                                                }
                                            },
                                            "if": {
                                                "properties": {
                                                    "tile_type": {
                                                        "enum": ["person"]
                                                    },
                                                    "errorCode": {
                                                        "enum": [2, 10]
                                                    }

                                                },
                                                "required":["errorCode"]
                                            },
                                            "then": {
                                                "required": ["errorCode", "errorText"]
                                            },
                                            "else": {
                                                "required": ["dataStamp"]
                                            }

                                        }
                                    }
                                },
                                "required": [
                                    "type",
                                    "tiles"
                                ]
                            }
                        }
                    },
                    "required": [
                        "groups"
                    ]
                }
            }
        },
        "required": [
            "views"
        ]
    }
}