Search code examples
jsonschema

Can JSON Schema require one value equal another?


consider the following schema:

{
  "properties":{
    "a": { "type":"string"},
    "meta": {
      "type": "object",
      "properties": {
        "a": { /*what might I put here to require that obj.a == obj.meta.a?*/ }
      }
    }
  }
}

Can I require a == meta.a somehow?

Totally not required, and not even applicable to the case that led me to this question, but it'd also be interesting to know if I could do any operations, like substrings, or exponentiation (if a had been a number).


Solution

  • Out of the box, no. JSON Schema doesn't define a way to reference parts of the instance, which means that it can't do those kinds of comparisons.

    However, I have a data vocab that you might be able to use if you're in .Net. I don't think any other languages support it yet.

    Basically, you'd have

    {
      "$schema": "https://json-everything.net/meta/data-2023",
      "properties": {
        "a": { "type":"string" },
        "meta": {
          "type": "object",
          "properties": {
            "a": {
              "data": {
                "const": "/a"
              }
            }
          }
        }
      }
    }
    

    For this schema,

    {
      "a": "string",
      "meta": {
        "a": "string"
      }
    }
    

    passes and

    {
      "a": "string",
      "meta": {
        "a": "also string"
      }
    }
    

    fails.

    What's happening is that the data keyword is building a schema by using its properties as keywords and dereferencing the values. Plain JSON Pointers are resolved against the instance, so this effectively builds

    {
      "const": "<whatever "a" is>"
    }
    

    in memory and evaluates meta.a against that.

    You can test this at my playground https://json-everything.net/json-schema