从架构中不存在的JSON对象中删除属性?

时间:2017-06-22 09:01:21

标签: python json jsonschema

我正在使用Python jsonschema来针对架构验证JSON文件。它很棒。但是现在我需要从架构中不存在的JSON中删除任何属性。

我知道根据the JSON Schema docs,我可以设置属性:

additionalProperties = false

拒绝任何具有其他属性的文件。但这只是拒绝属性,而不是删除它们。

删除它们的最佳方法是什么?

我想我可以编写自己的脚本:

  • 遍历JSON文件的每个叶节点
  • 检查架构中是否存在叶节点
  • 如果没有,则沿树向上走,直到找到确实存在的最高节点,然后在该点修剪分支。

我的问题是:是否有现成的Python库来执行此操作,还是需要编写一个?我用谷歌搜索,但没有任何成功。

2 个答案:

答案 0 :(得分:1)

您可以扩展验证器。类似的implementation is used for default values

有点晚了,但这是一个解决方案。

我扩展了验证器,以覆盖properties关键字的验证。如果实例中存在属性之一,但架构中不存在,则将其从实例中删除。

from jsonschema import Draft7Validator, validators

def extend_validator(validator_class):
    validate_properties = validator_class.VALIDATORS["properties"]

    def remove_additional_properties(validator, properties, instance, schema):
        for prop in list(instance.keys()):
            if prop not in properties:
                del instance[prop]

        for error in validate_properties(
            validator, properties, instance, schema,
        ):
            yield error

    return validators.extend(
        validator_class, {"properties" : remove_additional_properties},
    )

DefaultValidatingDraft7Validator = extend_validator(Draft7Validator)

# Example usage:
obj = {
    'foo': 'bar',
    'not_in_schema': 'no no no'
}
schema = {
    'properties': {
        'foo': {
            'type': 'string'
        }
    }
}

DefaultValidatingDraft7Validator(schema).validate(obj)
assert obj == {'foo': 'bar'}

答案 1 :(得分:0)

如果没有猴子修补 Validator 类中的 iter_errors()方法,我看不到直接的方法:

https://github.com/Julian/jsonschema/blob/master/jsonschema/validators.py#L296