django Model层常用验证器及自定义验证器详解


Posted in Python onJuly 15, 2020

在Django中,对数据进行校验有两种方式:一种是通过Form校验,一种是通过Model校验。在此,我对Model中的校验方法做下记录。

示例之前补充以下几点:

1、Django数据校验方式分为以下三步:

Model.clean_fields() 验证字段基本规则比如长度格式等;

Model.clean() 可自定义验证条件和报错信息;

Model.validate_unique() 为验证添加的唯一性约束。

2、此三步验证通过调用full_claen(exclude=None, validate_unique=True)来依次执行。

exclude:可以用来指定不需要执行校验的field。ModelForm也利用这个参数来将field排除。

validate_unique:用来指定是否需要执行Model.validate_unique()。

3、而full_clean()又是通过调用is_valid()方法来执行。

4、save()执行的时候是不会自动调用full_clean()来进行校验的。

校验应该在save()执行之前完成,你可以先在form进行校验,也可以在model中进行校验。但是,你必须确保通过这两个校验之后的数据是绝对没有问题的“干净”数据,然后再调用save()方法将数据存储入库。

5、校验中的错误处理

我们使用ValidationError来在Model.clean中抛出错误,这个错误信息将会存储在以NON_FIELD_ERRORS为key的字典中。这个key是用来存储对于整个model中的错误信息的。

如何获取校验的错误信息:

from django.core.exceptions import ValidationError, NON_FIELD_ERRORS
try:
  article.full_clean()
except ValidationError as e:
  non_field_errors = e.message_dict[NON_FIELD_ERRORS]

如何指定对于某个特定的field的校验错误信息:

class Article(models.Model):
  ...
  def clean(self):
    if self.status == 'draft' and self.pub_date is not None:
      # raise ValidationError({'pub_date': _('Draft entries may not have a publication date.')})
      raise ValidationError({'pub_date': 'Draft entries may not have a publication date.'})
    ...

如何指定多个field的校验错误信息:

class Article(models.Model):
  ...
  def clean(self):
    if self.status == 'draft' and self.pub_date is not None:
      raise ValidationError({'pub_date': 'Draft entries may not have a publication date.', 
                 'creator': 'Creator can't be null'})
    ...

如何指定全局性校验错误信息:

class Article(models.Model):
  ...
  def clean(self):
    if self.status == 'draft' and self.pub_date is not None:
      raise ValidationError('Draft entries may not have a publication date.')
    ...

进入正题:

一、如何使用验证器:

在验证某个字段的时候,在模型或者自定义form表单中传递一个 validators 参数用来指定验证器,进一步对数据进行过滤。

或者,通过model中的 Field类型 或者一些参数就可以指定。

比如 EmailValidator ,我们可以通过 指定字段类型为EmailField 来指定。

比如 MaxValueValidator ,我们可以通过 max_value 、max_length参数来指定。

class Interview(models.Model):
  feedback = models.TextField(max_length=1024, validators=[MinLengthValidator(20, message='不少于20字')], verbose_name='面试反馈')
  mail = models.EmailField(max_length=64, blank=True, null=True, verbose_name='邮箱')
  age= models.IntegerField(max_value=64, blank=True, null=True, verbose_name='年龄')

二、常用自带验证器:

1. MaxValueValidator :验证最大值。

2. MinValueValidator :验证最小值。

3. MinLengthValidator :验证最小长度。

4. MaxLengthValidator :验证最大长度。

5. EmailValidator :验证是否是邮箱格式。

6. URLValidator :验证是否是 URL 格式。

7. RegexValidator :如果还需要更加复杂的验证,那么我们可以通过正则表达式的验证。

class Demo(models.Model):
telephone = models.CharField(validators=[validators.RegexValidator("1[345678]\d{9}",message='请输入正确格式的手机号码!')])

三、自定义验证器:

方法:

如果你想要自定义model的校验,或者想要修改model的属性的话,就要重写clean()方法。

class Interview(models.Model):
  feedback = models.TextField(max_length=1024, validators=[MinLengthValidator(20, message='不少于20字')], verbose_name='面试反馈')
  mail = models.EmailField(max_length=64, blank=True, null=True, verbose_name='邮箱')
  age= models.IntegerField(max_value=64, blank=True, null=True, verbose_name='年龄'
  ...
 
  def clean(self):
    if self.result_1 == InterviewResult.FAIL and len(self.feedback) < 20:
      raise ValidationError({'feedback': '不少于20字'})

效果:

django Model层常用验证器及自定义验证器详解

django Model层常用验证器及自定义验证器详解

如果你想做一个全局性的错误提示,可以这样:

...
  def clean(self):
    if self.result_1 == InterviewResult.FAIL and len(self.feedback) < 20:
      raise ValidationError('不少于20字吧')

效果:

django Model层常用验证器及自定义验证器详解

以上这篇django Model层常用验证器及自定义验证器详解就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
分享15个最受欢迎的Python开源框架
Jul 13 Python
python微信跳一跳系列之自动计算跳一跳距离
Feb 26 Python
对Python中内置异常层次结构详解
Oct 18 Python
python利用插值法对折线进行平滑曲线处理
Dec 25 Python
python把转列表为集合的方法
Jun 28 Python
python多线程高级锁condition简单用法示例
Nov 07 Python
python飞机大战pygame碰撞检测实现方法分析
Dec 17 Python
借助Paramiko通过Python实现linux远程登陆及sftp的操作
Mar 16 Python
django模型类中,null=True,blank=True用法说明
Jul 09 Python
虚拟机下载python是否需要联网
Jul 27 Python
Python离线安装openpyxl模块的步骤
Mar 30 Python
Python下opencv使用hough变换检测直线与圆
Jun 18 Python
浅谈Django前端后端值传递问题
Jul 15 #Python
浅谈python出错时traceback的解读
Jul 15 #Python
Django视图、传参和forms验证操作
Jul 15 #Python
一文解决django 2.2与mysql兼容性问题
Jul 15 #Python
django 模型字段设置默认值代码
Jul 15 #Python
django序列化时使用外键的真实值操作
Jul 15 #Python
Django:使用filter的pk进行多值查询操作
Jul 15 #Python
You might like
PHP缓存技术的使用说明
2011/08/06 PHP
利用curl抓取远程页面内容的示例代码
2013/07/23 PHP
可以保证单词完整性的PHP英文字符串截取代码分享
2014/07/15 PHP
php实现给二维数组中所有一维数组添加值的方法
2017/02/04 PHP
Laravel 实现Controller向blade前台模板赋值的四种方式小结
2019/10/22 PHP
baidu博客的编辑友情链接的新的层窗口!经典~支持【FF】
2007/02/09 Javascript
js 获取服务器控件值的代码
2010/03/05 Javascript
IE8 中使用加速器(Activities)
2010/05/14 Javascript
为JavaScript提供睡眠功能(sleep) 自编译JS引擎
2010/08/16 Javascript
javascript里模拟sleep(两种实现方式)
2013/01/25 Javascript
判断客户浏览器是否支持cookie的示例代码
2013/12/23 Javascript
js图片延迟技术一般的思路与示例
2014/03/20 Javascript
Jquery图片延迟加载插件jquery.lazyload.js的使用方法
2014/05/21 Javascript
JavaScript时间转换处理函数
2015/04/14 Javascript
js数组去重的方法汇总
2015/07/29 Javascript
javascript定义类和类的实现实例详解
2015/12/01 Javascript
浅析Proxy可以优化vue的数据监听机制问题及实现思路
2018/11/29 Javascript
js操作两个json数组合并、去重,以及删除某一项元素
2020/09/22 Javascript
手动实现vue2.0的双向数据绑定原理详解
2021/02/06 Vue.js
基于python的汉字转GBK码实现代码
2012/02/19 Python
PyMongo安装使用笔记
2015/04/27 Python
Python实现matplotlib显示中文的方法详解
2018/02/06 Python
python将txt文件读取为字典的示例
2018/12/22 Python
Python基于stuck实现scoket文件传输
2020/04/02 Python
Python+Selenium随机生成手机验证码并检查页面上是否弹出重复手机号码提示框
2020/09/21 Python
html5 canvas的绘制文本自动换行的示例代码
2018/09/17 HTML / CSS
英国第一的购买便宜玩具和游戏的在线购物网站:Bargain Max
2018/01/24 全球购物
职工趣味运动会方案
2014/02/10 职场文书
致垒球运动员加油稿
2014/02/16 职场文书
大专生求职信
2014/06/29 职场文书
自愿离婚协议书范本
2015/01/26 职场文书
2015年维修工作总结
2015/04/25 职场文书
2015年毕业实习工作总结
2015/05/29 职场文书
电影建党伟业观后感
2015/06/01 职场文书
MySQL基础(一)
2021/04/05 MySQL
sql server偶发出现死锁的解决方法
2022/04/10 SQL Server