• Form组件的验证流程及扩展(钩子)


    Form组件的验证流程及扩展(钩子)

    常用的form

    class TestForm(Form):
        t1 = fields.CharField(
            widget=widgets.Textarea  # 输入框
        )
        t2 = fields.CharField(
            widget=widgets.CheckboxInput  # 单选框
        )
        t3 = fields.MultipleChoiceField(
            choices=[(1, '篮球'), (2, '足球')],  # 多选框的内容
            widget=widgets.CheckboxSelectMultiple  # 多选框
        )
        t4 = fields.ChoiceField(
            choices=[(1, '篮球'), (2, '足球')],
            widget=widgets.RadioSelect   # 单选 互斥
        )
        t5 = fields.FileField(
            widget=widgets.FileInput  # 文件  最终获得是文件对象
        )
    
    
    def test(request):
        obj = TestForm(initial={'t3': [2, ]})  # 多选的默认
        return render(request, 'test.html', {'obj': obj})
    

    前端

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
    </head>
    <body>
        {{ obj.t1 }}
        {{ obj.t2 }}
        {{ obj.t3 }}
        {{ obj.t4 }}
        {{ obj.t5 }}
    </body>
    </html>
    

    Form组件的验证流程

    关键点是返回值

    • 进行正则验证
    • 循环所有的字段,加入self.fields中并执行相应的函数clean_xxx,xxx是字段的名字
    • 自己定义的高级验证一定要有返回值,默认是自己

    源码的寻找循序:
    is_valid -> errors -> full_clean -> self._clean_fields()

    源码中的full_clean

    self._clean_fields()  # 对定义的字段函数进行验证
    self._clean_form()   # clean整体验证
    self._post_clean()   # 最后自定义验证 一般不适用,需要自己写错误验证
    

    1 自定义函数进行验证

    自定义的函数是对每个字段进行验证,

    from django.core.exceptions import ValidationError
    
    
    class TestForm(Form):
        user = fields.CharField()
        pwd = fields.CharField()
    
        def clean_user(self):
            v = self.cleaned_data['user']
            if models.Students.objects.filter(name=v).count():
                raise ValidationError('用户名已经存在', code='invalid')  # 默认是invalid 还可以是其他的required
            else:
                pass
            return self.cleaned_data['user']  # 一定要有返回值 否则cleaned_data就是None,
            # 没有改变就把自身返回
    
        def clean_pwd(self):
            return self.cleaned_data['pwd']  # self代表的是obj对象
    

    2 整体验证

    使用clean对整体进行验证,内部已经提供了异常处理

    class TestForm(Form):
        user = fields.CharField()
        pwd = fields.CharField()
    
        def clean_user(self):
            v = self.cleaned_data['user']
            if models.Students.objects.filter(name=v).count():
                raise ValidationError('用户名已经存在', code='invalid')  # 默认是invalid 还可以是其他的required
            else:
                pass
            return self.cleaned_data['user']  # 一定要有返回值 否则cleaned_data就是None,
            # 没有改变就把自身返回
    
        def clean_pwd(self):
            return self.cleaned_data['pwd']
    
        def clean(self):
            user = self.cleaned_data.get('user')
            email = self.cleaned_data.get('email')
            if models.Students.objects.filter(user=user, email=email).count():
                raise ValidationError('用户名和邮箱联合存在')
            return self.cleaned_data
    

    3 在默认正则中添加正则

    需要导入一个模块

    关键在validators=[],在内部添加正则,如第一个没有通过验证,后面的也就不用进行验证了

    from django.core.validators import RegexValidator
    
    class TestForm(Form):
        # user = fields.CharField(validators=[])
        user = fields.CharField(
            validators=[RegexValidator(r'^[0-9]+$', '请输入数字'), RegexValidator(r'^159[0-9]+$', '数字必须以159开头')],
        )
        pwd = fields.CharField()
    

    总结:

    • 字段 = 默认正则表达式

        额外的正则
        from django.forms import Form
        from django.forms import widgets
        from django.forms import fields
        from django.core.validators import RegexValidator
         
        class MyForm(Form):
        	user = fields.CharField(
        		validators=[RegexValidator(r'^[0-9]+$', '请输入数字'), RegexValidator(r'^159[0-9]+$', '数字必须以159开头')],
        	)
      
    • clean_字段,必须返回值

    • clean()
      有返回值:cleaned_data = 返回值
      无返回值:cleaned_data = 原来的值

    参考:
    http://www.cnblogs.com/wupeiqi/articles/6144178.html

  • 相关阅读:
    delphi 如何让ScrollBox的内容与滚动条一起实时滚动
    C# Wpf集合双向绑定
    C# Wpf异步修改UI,多线程修改UI(二)
    C# 自定义线程修改UI(一)
    WPF FindName()查找命名注册的元素
    数据绑定
    WPF绑定Binding及模式
    WPF-Binding的源
    WPF-Binding对数据的检验
    WPF-数据转换
  • 原文地址:https://www.cnblogs.com/Python666/p/7142442.html
Copyright © 2020-2023  润新知