一、局部钩子
命名规则为clean_对象名称,例如上面定义了username、pwd对象,那么可以定义clean_username、clean_pwd的局部钩子进行规则校验
1、例子:定义一个手机号校验的局部钩子
def clean_phone(self): value = self.cleaned_data.get('phone') # 没有通过校验规则 抛出ValidationError if not re.match(r'^1[3-9]\d{9}$',value): raise ValidationError('手机号格式不正确') # 通过校验规则 返回当前的值 return value
2、例子:定义局部钩子,判断部门名称是否已存在
from django import forms from crm import models class DepartForm(forms.ModelForm): class Meta: model = models.Depart fields = '__all__' error_messages = { 'depart_name': { 'required': '不能为空', }, 'depart_desc': { 'required': '不能为空', }, } def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) # 批量更新class属性 for field in self.fields.values(): field.widget.attrs.update({'class': 'form-control'}) # 定义局部钩子,判断部门名称是否已存在 def clean_depart_name(self): depart_name_new = self.cleaned_data.get('depart_name', None) if not models.Depart.objects.filter(depart_name=depart_name_new).exists(): # 注意局部钩子返回的是要校验的这个值,全局钩子返回的是self.cleaned_data return depart_name_new # self.add_error('depart_name', '部门名称已存在!') raise forms.ValidationError('部门名称已存在')
配置错误信息时,self.add_error和raise ValidationError这两种方法都可以
导入方法有2种
from django.forms import ValidationError 或者 from django.core.exceptions import ValidationError
抛出异常时使用ValidationError,则错误信息在__all__字典中,模板中通过{{form_obj.non_field_error.0}}获取错误信息
raise ValidationError('部门名称已存在')
如果使用self.add_error方法,则是给指定字段添加错误信息
self.add_error('depart_name', '部门名称已存在')
二、全局钩子
编写全局钩子预留的clean方法,可以获取到多个字段并进行校验
1、例子:定义一个校验2次输入密码是否一致的全局钩子
def clean(self): pwd = self.cleaned_data.get('pwd') re_pwd = self.cleaned_data.get('re_pwd') # 通过校验 返回self.cleaned_data if pwd == re_pwd: return self.cleaned_data # 没有通过校验 抛出ValidationError # self.add_error('re_pwd','两次密码不一致!') raise ValidationError('两次密码不一致') 前端可以通过form_obj.errors.__all__ 获取到内置校验器的全部错误信息 不能通过__all__来调取全局钩子的错误信息,需要通过对象的non_field_errors来获取错误信息列表 {{ form_obj.non_field_errors.0 }}