根据 Python 中的 JSON 架构过滤 JSON 数据

Filter JSON data against JSON schema in Python

我正在寻找 Python 模块来根据架构过滤 JSON 数据。

例如, 有 JSON 数据:

{
    "system" : {
        "state" : "enabled",
        "id" : 5,
        "keys" : [
            { "key_id": 12, "key": "filename.key" }
        ]
    }
}

还有 JSON 模式:

{
    "system": {
        "id": "system",
        "required": true,
        "type": "object",
        "properties": {
            "state": {
                "id": "state",
                "required": true,
                "type": "string"
            },
            "id": {
                "id": "id",
                "required": true,
                "type": "number"
            }
        }
    }
}

如您所见,架构不包含 "keys" 属性.

我需要一些工具,它可以使用模式过滤 JSON 数据并提供以下 JSON 作为输出:

{
    "system" : {
        "state" : "enabled",
        "id" : 5
    }
}

您可以使用 jsonschema 根据架构验证您的 json,请查看此示例

from jsonschema import validate

schema = {"type" : "object","properties" : { "price" : {"type" : "number"},"name" : {"type" : "string"},},}
validate(instance={"name" : "Eggs", "price" : 34}, schema=schema)

如果 validate() 没有抛出异常,则实例有效

JSON 模式的目的是根据定义的模式验证给定的 JSON 输入。正如@Relequestual 在评论中所说,您不能使用 JSON 模式直接过滤掉字段。

如果您只需要删除 keys 字段,则根本不需要使用 JSON 架构。您可以简单地从 JSON 输入中删除该字段。

如果您需要从输入中过滤掉一堆意外的字段,您可以使用 JSON 架构来 identify 这些字段。但是您需要手动或使用其他库进行过滤部分,因为 JSON 模式无法为您完成。

您可以使用 additionalProperties 字段来限制意外键。

{
  "type":"object",
  "required":false,
  "properties":{
    "system": {
        "id": "system",
        "required": true,
        "type": "object",
        "properties": {
            "state": {
                "id": "state",
                "required": true,
                "type": "string"
            },
            "id": {
                "id": "id",
                "required": true,
                "type": "number"
            }
        },
        "additionalProperties": false
    }
  }
}

这将给出如下所示的验证错误

Message: Property 'keys' has not been defined and the schema does not allow additional properties. Schema path: #/properties/system/additionalProperties

这可能不是您要找的确切答案。但希望它能有所帮助。

由于没有针对架构过滤 JSON 数据的工具,我已按如下方式解决我的任务。

已创建预期 JSON 文件的模板。实际上它已经过滤了 JSON 文件,但没有数据。

{
    "system" : {
        "state" : "",
        "id" : 0
    }
}

然后浏览数据文件和模板文件,将两个文件中都存在的属性的值从一个复制到另一个。