JSON 架构 - 外键 (FK) 验证

问题描述 投票:0回答:2

我有以下 JSON 模式:

架构A:

{
  "$schema": "http://json-schema.org/draft-04/hyper-schema#",
  "title": "A",
  "type": "object",
  "properties": {
    "id": {
      "type": "string"
    },
    "name": {
      "type": "string"
    },
    "entityBId": {
      "type": "string"
    }
  },
  "required": [
    "name",
    "entityBId"
  ],
  "links": [
    {
      "rel": "B",
      "href": "myapi/EntityB?id={entityBId}"
    }
  ]
}

模式B

{
  "$schema": "http://json-schema.org/draft-04/schema#",
  "title": "B",
  "type": "object",
  "properties": {
    "id": {
      "type": "string"
    },
    "name": {
      "type": "string"
    }
  },
  "required": [
    "name"
  ]
}

我试图弄清楚是否有一种方法可以运行基于带有外部链接/引用的 JSON 模式的完整性检查之类的东西。 例如:当我收到一个 entityBId = 1 的对象 A 时,我想在链接 href 中声明的端点中运行 GET 来获取该实体 B,并检查接收到的 id 中是否存在有效对象。 它将像深度验证一样运行,并且在没有定义数据库模式的场景中非常有用。

json jsonschema json-schema-validator
2个回答
0
投票

根据 Raj Kamal 的建议,我制作了自己的“链接验证”。 有一个函数可以在模式上查找链接属性并直接在数据库上验证外部引用,如果未找到有效引用则抛出异常。


0
投票

JSON 模式不是 DBMS,但我找到了解决方法。

但这并不是完全万无一失的。在实例中添加或删除 B 键时,需要更新引用的架构 (B)。但是,如果不这样做,您将在 B 实例中收到验证错误。

实施

  1. 让 B 对象 ID 成为模式实例中的对象键而不是属性:
{
  "b1": {
    "name": "The Bee Movie"
  }
  // ...
}
  1. 更新 B 的架构:
{
  "$schema": "http://json-schema.org/draft-06/hyper-schema#",
  "title": "B",
  "type": "object",
  "propertyNames": {
    "description": "B ID",
    "enum": [
      // keep list of existing B keys updated
      "b1"
      // ...
    ]
    // add other constraints on the ID here (pattern, minLength...)
  }
  "properties": {
    "name": {
      "type": "string"
    }
  },
  "required": [
    "name"
  ]
}
  1. 现在,架构 A 中的 $ref 架构 B 使用 JSON 指针来访问 propertyNames 子架构:
{
  "$schema": "http://json-schema.org/draft-06/hyper-schema#",
  "title": "A",
  "type": "object",
  "properties": {
    "id": {
      "type": "string"
    },
    "name": {
      "type": "string"
    },
    "entityBId": {
      "$ref": "B.json#/propertyNames"
    }
  },
  "required": [
    "name",
    "entityBId"
  ],
  "links": [
    {
      "rel": "B",
      "href": "myapi/EntityB?id={entityBId}"
    }
  ]
}

你就得到了它。尽管在此示例中没有必要,但请考虑使用对象键而不是 A 的 ID 属性,以与 B 相同的方式保持一致性。

最新问题
© www.soinside.com 2019 - 2025. All rights reserved.