luk*_*kik 2 python validation cerberus
正在验证.csv文件,我想以用户习惯的格式给出验证结果。为了使用Cerberus,我让用户在文件中定义验证规则.yaml。
架构.yaml
Rules:
Rule1:
maxlength: 10
Rule2:
allowed: ["MO", "TU", "WE", "TH", "FR", "SA", "SU"]
Rule3:
required: True
Run Code Online (Sandbox Code Playgroud)
然后,我将这些规则映射到 CSV 文件中适用的列。
csv_fields.yaml
Fields:
1:
rules:
- Rule1
- Rule2
2:
rules:
- Rule2
- Rule3
3:
rules:
- Rule1
- Rule3
Run Code Online (Sandbox Code Playgroud)
样本文件.csv
下面是一个包含三列的示例文件:first_name、day_of_week和is_employed。
Peter, XX, True
Run Code Online (Sandbox Code Playgroud)
为了使用 Cerberus 进行验证,我将文档密钥rules中定义的内容与文件中的进行交叉引用。这很容易做到,因为文件在 python 中以键值格式读取为字典。rulescsv_fields.yamlRulesschema.yaml.yaml
我的问题
在上面的示例数据中,cerberus 会抛出错误'day_of_week': ['unallowed value XX'],但用户不知道什么规则触发了此错误。
我期待告诉用户的是,该错误unallowed value XX是由Rule2用户所知触发的Rule2,而不是由 Cerberus 技术特定定义触发的。
有没有办法实现这一点,即使这意味着以schema.yaml不同的方式定义?
我查看了Cerberus 错误部分,但似乎找不到方法来执行此操作。
更新:
所以我尝试在schema.yamlmeta中的规则定义中添加一个字段
Rules:
Rule1:
maxlength: 10
meta: {'rule_name': "Rule1"}
Run Code Online (Sandbox Code Playgroud)
但是当我测试时,我似乎无法从引发的错误中访问此元密钥,因为我无法在document_error_tree甚至中找到它schema_error_tree。
我和你在同一个地方,我会告诉你我做了什么。
创建了一个自定义 error_handler 并在错误消息前面添加了人类可读的键。
from cerberus.errors import BasicErrorHandler
class CustomErrorHandler(BasicErrorHandler):
def __init__(self, schema):
self.custom_defined_schema = schema
def _format_message(self, field, error):
return self.custom_defined_schema[field].get('meta', {}).get('rule_name', field) + ': ' + super(CustomErrorHandler, self)._format_message(field, error)
val = Validator(schema, error_handler=CustomErrorHandler(schema))
Run Code Online (Sandbox Code Playgroud)
这就是我所做的,希望对你有用。