如何动态验证任意字段?

How to dynamically validate an arbitrary field?

对于我的一个 Django 模型,我有一个由输入字段组成的编辑模板。然而,与标准表单不同的是,每当这些输入发生变化时,我都会发出一个 AJAX 请求来保存那个单独的字段。我的 AJAX 端点基本上是这样的:

def update_field(request, mod_id, field, value, element_id):
    mod = Model.objects.get(id=mod_id)
    setattr(mod, field, value)
    mod.save()
    return json.dumps({'element_id': element_id})

然而,这是一种非常基本且可能幼稚的方法。在调用 setattr 并保存之前,我想验证输入(即 value)对于 modelField field 所指的任何内容均有效,其中 field 是一个字符串。

有没有办法验证这一点,给定一些输入 value 和模型上的一些字段名称 field

您可以使用 clean_fields() 函数执行模型字段验证。此方法验证我们模型上的所有字段。

您可以这样做:

from django.core.exceptions import ValidationError
from django.db import models

class MyModel(models.Model)

    ...

    def clean_fields(self):
        if self.my_field_name != 'some_valid_value': # write your logic for validity here
            raise ValidationError('Invalid value') # raise validation error
        return super(MyModel, self).clean_fields()

使用任何模型级清理方法都存在一个问题,即引发的 ValidationError 是为模型设置的,因为它是按字段名称键入的。在我的例子中,我只处理一个字段,我只想处理来自那个字段的 ValidationErrors。要真正满足我在这里的要求(即 "Is there a way to validate some given some input value for some field name on some model?"),我认为这是合适的解决方案:

def update_field(request, mod_id, field, value, element_id):
    mod = Model.objects.get(id=mod_id)
    try:
        modelfield = mod._meta.get_field(field)
        setattr(mod, field, modelfield.clean(value, mod))
    except ValidationError as e:
        # This can only be raised for errors on modelfield, not on any errors for `mod`
        return json.dumps({'errormsg': str(e)})
    mod.save()
    return json.dumps({'element_id': element_id})