Django ModelForm表单验证
ModelForm
在使用Model和Form时,都需要对字段进行定义并指定类型,通过ModelForm则可以省去From中字段的定义
应用场景:定制model admin 的时候可以使用。适用于小业务架构。
ModelForm
a. class Meta:
model, # 对应Model的
fields=None, # 字段
exclude=None, # 排除字段
labels=None, # 提示信息
help_texts=None, # 帮助提示信息
widgets=None, # 自定义插件
error_messages=None, # 自定义错误信息(整体错误信息from django.core.exceptions import NON_FIELD_ERRORS)
field_classes=None # 自定义字段类 (也可以自定义字段)
localized_fields=('birth_date',) # 本地化,如:根据不同时区显示数据
如:
数据库中
2016-12-27 04:10:57
setting中的配置
TIME_ZONE = 'Asia/Shanghai'
USE_TZ = True
则显示:
2016-12-27 12:10:57
b. 验证执行过程
is_valid -> full_clean -> 钩子 -> 整体错误 c. 字典字段验证
def clean_字段名(self):
# 可以抛出异常
# from django.core.exceptions import ValidationError
return "新值"
d. 用于验证
model_form_obj = XXOOModelForm()
model_form_obj.is_valid()
model_form_obj.errors.as_json()
model_form_obj.clean()
model_form_obj.cleaned_data
e. 用于创建
model_form_obj = XXOOModelForm(request.POST)
#### 页面显示,并提交 #####
# 默认保存多对多
obj = form.save(commit=True)
# 不做任何操作,内部定义 save_m2m(用于保存多对多)
obj = form.save(commit=False)
obj.save() # 保存单表信息
obj.save_m2m() # 保存关联多对多信息 f. 用于更新和初始化
obj = model.tb.objects.get(id=1)
model_form_obj = XXOOModelForm(request.POST,instance=obj)
... PS: 单纯初始化
model_form_obj = XXOOModelForm(initial={...})
views.py
class UserInfoModelForm(forms.ModelForm):
class Meta(object):
model = models.UserInfo
fields = '__all__' # 请求处理
class ModelFormTest(View):
def get(self, request):
# ModelForm 创建对象
verify_obj = UserInfoModelForm()
return render(request, 'modelForm.html', {'verify_obj': verify_obj})
models.py
class UserType(models.Model):
caption = models.CharField(max_length=32) class UserInfo(models.Model):
username = models.CharField(verbose_name='用户名', max_length=32)
email = models.EmailField()
user_type = models.ForeignKey(to=UserType, to_field='id', on_delete=models.SET_NULL,null=True)
注:verbose_name 为django admin管理数据 的时候显示 的字段。在模板中渲染时,调用modelForm对象实例也可以显示对应的中文
{{ verify_obj.as_p }}
{{ verify_obj.as_ul }}
{{ verify_obj.as_table }}
modelForm.html
<form action="/modelformtest/" method="post">
{% csrf_token %}
{{ verify_obj.as_p }}
<input type="submit" value="提交">
</form>
访问效果
-------------------------------------------------------------------------------------------------------------
只展示指定列 fields =
class UserInfoModelForm(forms.ModelForm):
class Meta(object):
model = models.UserInfo
# fields = '__all__'
fields = ['username', ]
排除指定列 :exclude = ['xxx',...]
class UserInfoModelForm(forms.ModelForm):
class Meta(object):
model = models.UserInfo
# fields = '__all__'
# fields = ['username', ]
exclude = ['username']
labels 效果等于models.py里面定义数据表字段时的 verbose_name='xxx'
为对输入字段自定义提示语
views.py
class UserInfoModelForm(forms.ModelForm):
class Meta(object):
model = models.UserInfo # 从哪个models 数据表里面获取字段
fields = '__all__' # 展示哪些字段
labels = { # 生成html标签的对应input标签前面的提示
'username': 'lables 用户名',
'email': '邮箱',
'user_type': '用户类型'
}
class ModelFormTest(View):
def get(self, request):
# ModelForm 创建对象
verify_obj = UserInfoModelForm()
return render(request, 'modelForm.html', {'verify_obj': verify_obj})
modelForm.html
<form action="/modelformtest/" method="post">
{% csrf_token %}
{{ verify_obj.as_p }}
<input type="submit" value="提交">
</form>
------------------------------------------------------------------------
help_texts=None, # 帮助提示信息
views.py
class UserInfoModelForm(forms.ModelForm):
class Meta(object):
model = models.UserInfo # 从哪个models 数据表里面获取字段
fields = '__all__' # 展示哪些字段
help_texts = { # 提示信息
'username': '用户名哦',
'email': '邮箱啊'
}
class ModelFormTest(View):
def get(self, request):
# ModelForm 创建对象
verify_obj = UserInfoModelForm()
return render(request, 'modelForm.html', {'verify_obj': verify_obj})
html
{{ verify_obj.as_p }}
--------------------------------------------------------------------
widgets=None, # 自定义标签类型插件
wiews.py
class UserInfoModelForm(forms.ModelForm):
class Meta(object):
model = models.UserInfo # 从哪个models 数据表里面获取字段
fields = '__all__' # 展示哪些字段
widgets = {
'username': forms_widgets.Textarea(attrs={'class': 'test-class'})
}
class ModelFormTest(View):
def get(self, request):
# ModelForm 创建对象
verify_obj = UserInfoModelForm()
return render(request, 'modelForm.html', {'verify_obj': verify_obj})
html
<form action="/modelformtest/" method="post">
{% csrf_token %}
{{ verify_obj.as_p }}
<input type="submit" value="提交">
</form>
--------------------------------------------------------------------------------------------
error_messages = {'字段名': {'错误类型': '错误提示', ... }}
class UserInfoModelForm(forms.ModelForm):
class Meta(object):
model = models.UserInfo # 从哪个models 数据表里面获取字段
fields = '__all__' # 展示哪些字段
error_messages = {
'email': {
'required': '必填',
'invalid': '邮箱格式错误'
},
'username': {
'max_length': '太长了',
'min_length': '太短了',
}
}
class ModelFormTest(View):
def get(self, request):
# ModelForm 创建对象
verify_obj = UserInfoModelForm()
return render(request, 'modelForm.html', {'verify_obj': verify_obj}) def post(self, request):
# 获取所有数据
# 每条数据请求的验证
# 成功显示正确信息
# 失败,给出错误提示
# 验证时将request.POST 传递给验证类,实例化验证对象
# verify_obj = MyFm(request.POST)
verify_obj = UserInfoModelForm(request.POST) verify_result = verify_obj.is_valid() # 验证是否通过,返回True/False
if not verify_result:
return render(request, 'modelForm.html', {'verify_obj': verify_obj})
# 整体错误信息使用 '__all__' 代表所有字段
error_messages = {
'__all__': {
'required': '必填',
'invalid': '格式错误'
},
}
生成html浏览器查看效果
-------------------------------------------
field_classes 更改原有字段生成的html标签类型
views.py
class UserInfoModelForm(forms.ModelForm):
class Meta(object):
model = models.UserInfo # 从哪个models 数据表里面获取字段
fields = '__all__' # 展示哪些字段
from django.forms import fields as form_fields
field_classes = {
'email':form_fields.URLField
}
-------------------------------------------------------------------------------------------------
localized_fields=('birth_date',) # 将数据本地化显示,如:根据不同时区显示数据
前提:
需要在settings.py中设置好本地的时区
# setting中的配置
TIME_ZONE = 'Asia/Shanghai' # 时区
USE_TZ = True # 启用本地时区
views.py
localized_fields=('birth_date',) # 本地化,如:根据不同时区显示数据
# 如数据库中存的 2016-12-27 04:10:57
# 则前端显示:2016-12-27 12:10:57
ModelForm 的数据库保存方式
验证有效,直接使用验证实例.save() 保存到数据库
views.py
class ModelFormTest(View):
def get(self, request):
# ModelForm 创建对象
verify_obj = UserInfoModelForm()
return render(request, 'modelForm.html', {'verify_obj': verify_obj}) def post(self, request):
# 获取所有数据
# 每条数据请求的验证
# 成功显示正确信息
# 失败,给出错误提示
# 验证时将request.POST 传递给验证类,实例化验证对象
# verify_obj = MyFm(request.POST)
verify_obj = UserInfoModelForm(request.POST)
if verify_obj.is_valid():
# 默认保存多对多 :第三张表的数据
verify_obj.save()
# 不做任何操作,内部定义 save_m2m(用于保存多对多)
#verify_obj.save(commit=False)
#verify_obj.save() # 保存单张表信息
#verify_obj.save_m2m() # 保存关联多对多 第三张表的信息
models.py
数据表结构UserInfo UserType UserGroup
UserInfo ---> UserType 一对多
UserInfo<----> UserGroup 多对多
class UserType(models.Model):
caption = models.CharField(max_length=32) def __str__(self):
return self.caption class UserGroup(models.Model):
name = models.CharField(max_length=32) class UserInfo(models.Model):
username = models.CharField(verbose_name='用户名', max_length=32)
email = models.EmailField()
user_type = models.ForeignKey(to=UserType, to_field='id', on_delete=models.SET_NULL,null=True)
u_in_g = models.ManyToManyField(UserGroup)
-----------------------------------------------------------------------
应用案例:用户列表 查看/编辑用户信息,保存到数据库
models.py
UserInfo 表 user_type字段外键UserType id字段
UserInfo 表u_in_g 字段外键 多对多 UserGroup表id字段
from django.db import models # Create your models here. class UserType(models.Model):
caption = models.CharField(max_length=32) def __str__(self):
return self.caption class UserGroup(models.Model):
name = models.CharField(max_length=32) def __str__(self):
return self.name class UserInfo(models.Model):
username = models.CharField(verbose_name='用户名', max_length=32)
email = models.EmailField()
user_type = models.ForeignKey(to=UserType, to_field='id', on_delete=models.SET_NULL,null=True)
u_in_g = models.ManyToManyField(UserGroup)
查已保存的数据信息展示给前端
ModelForm 指定instance 数据对象(自定义的数据表 具体的查询结果对象),可以显示给前端
例如:user_html_obj = UserInfoModelForm(instance=user_data)
更新数据库中的信息
例如:
user = models.UserInfo.objects.filter(id=uid).first()
mf_obj = UserInfoModelForm(request.POST, instance=user)
mf_obj.save()
验证post请求的数据有效。更新到指定的查询结果中去,如果不指定instance 则为新增数据操作
views.py
class UserList(View):
def get(self, request):
users = models.UserInfo.objects.all().select_related('user_type')
return render(request, 'modelForm_user_lisst.html' , {'users': users}) class UserEdit(View):
def get(self, request, uid):
user_data = models.UserInfo.objects.filter(id=uid).first()
print('数据查询:', type(user_data))
# 将数据库查询出来的数据对象
user_html_obj = UserInfoModelForm(instance=user_data)
return render(request, 'ModelForm_user_edit.html', {'user_html_obj': user_html_obj, 'uid': uid})
pass def post(self, request,uid):
user = models.UserInfo.objects.filter(id=uid).first()
mf_obj = UserInfoModelForm(request.POST, instance=user)
# 更新的数据符合要求,保存到数据库
if mf_obj.is_valid():
mf_obj.save()
else:
print(mf_obj.errors.as_json)
return render(request, 'ModelForm_user_edit.html', {'user_html_obj': mf_obj, 'uid': uid})
modelForm的钩子
验证顺序:is_valid-->full_clean-->clean_fields-->clean_form-->_post_clean
1、在验证数据合法,保存到数据库之前,对验证的数据进行修改
定义 def clean_字段名():函数 对self.cleaned_data中获取到的字段进行修改
class UserInfoModelForm(forms.ModelForm):
class Meta(object):
#..................... def clean_username(self):
old_username = self.cleaned_data.get('username')
return old_username + '呵呵'
增加不存储于数据库的字段
应用场景:是否记住登录
views.py
from django.shortcuts import render
from django.views import View
from django import forms from modelForm_study import models
from django.forms import widgets as forms_widgets
# Create your views here. class UserInfoModelForm(forms.ModelForm): # 在生成前端标签的时候增加的字段(相比数据库表里面的字段)
rember_login = forms.CharField(
widget=forms_widgets.CheckboxInput(),
required=False # 是否必填
)
class Meta(object):
model = models.UserInfo # 从哪个models 数据表里面获取字段
fields = '__all__' # 展示哪些字段
from django.forms import fields as form_fields
# field_classes = { # 改变原有字段类型
# 'email':form_fields.URLField
# }
error_messages = {
'__all__': {
'required': '必填',
'invalid': '格式错误'
},
'email': {
'required': '必填',
'invalid': '邮箱格式错误'
},
'username': {
'max_length': '太长了',
'min_length': '太短了',
}
}
help_texts = { # 提示信息
'username': '用户名哦',
'email': '邮箱啊'
}
labels = { # 生成html标签的对应input标签前面的提示
'username': 'lables 用户名',
'email': '邮箱',
'user_type': '用户类型',
'u_in_g': '所在组',
}
# widgets = {
# 'username': forms_widgets.Textarea(attrs={'class': 'test-class'})
# }
# fields = ['username', ]
# exclude = ['username'] # def clean_username(self):
# old_username = self.cleaned_data.get('username')
# return old_username + '呵呵'
# 请求处理 class UserList(View):
def get(self, request):
users = models.UserInfo.objects.all().select_related('user_type')
return render(request, 'modelForm_user_lisst.html' , {'users': users}) class UserEdit(View):
def get(self, request, uid):
user_data = models.UserInfo.objects.filter(id=uid).first()
print('数据查询:', type(user_data))
# 将数据库查询出来的数据对象
user_html_obj = UserInfoModelForm(instance=user_data)
return render(request, 'ModelForm_user_edit.html', {'user_html_obj': user_html_obj, 'uid': uid})
pass def post(self, request,uid):
user = models.UserInfo.objects.filter(id=uid).first()
mf_obj = UserInfoModelForm(request.POST, instance=user)
# mf_obj = UserInfoModelForm(request.POST) # 更新的数据符合要求,保存到数据库
if mf_obj.is_valid():
print(mf_obj.cleaned_data)
mf_obj.save()
if mf_obj.cleaned_data.get('rember_login'):
# 记住登录用户xxx时间内免登陆,设置cookie ,session等
print('是否记住登录:', mf_obj.cleaned_data.get('rember_login'))
else:
print(mf_obj.errors.as_json)
return render(request, 'ModelForm_user_edit.html', {'user_html_obj': mf_obj, 'uid': uid})
Django ModelForm表单验证的更多相关文章
- python运维开发(十九)----Django后台表单验证、session、cookie、model操作
内容目录: Django后台表单验证 CSRF加密传输 session.cookie model数据库操作 Django后台Form表单验证 Django中Form一般有2种功能: 1.用于做用户提交 ...
- django form表单验证
一. django form表单验证引入 有时时候我们需要使用get,post,put等方式在前台HTML页面提交一些数据到后台处理例 ; <!DOCTYPE html> <html ...
- django from表单验证
django from表单验证 实现:表单验证 工程示例: urls.py 1 2 3 4 5 6 7 8 9 from django.conf.urls import url from djan ...
- Django(5) session登录注销、csrf及中间件自定义、django Form表单验证(非常好用)
一.Django中默认支持Session,其内部提供了5种类型的Session供开发者使用: 数据库(默认) 缓存 文件 缓存+数据库 加密cookie 1.数据库Session 1 2 3 4 5 ...
- Django实现表单验证、CSRF、cookie和session、缓存、数据库多表操作(双下划綫)
通常验证用户输入是否合法的话,是前端js和后端共同验证的,这是因为前端js是可以被禁用的,假如被禁用了,那就没法用js实现验证合法与否了,也就是即使用户输入的不合法,但是也没提示,用户也不知道怎么输入 ...
- django book表单验证学习
django提供了强大的表单验证功能form 个人认为是把html代码封装到form里面,就像封装models中的数据一样.而且带有强大的验证功能,不需要后台再去写一堆乱七八糟的验证 具体操作查看dj ...
- Django之表单验证
对于前端的表单进行验证的方法,从最简单的js到基于XML传输的Ajax,再到cookie的免认证,现在Django为我们提供了自带的表单验证方法. views.py: from django impo ...
- 使用ModelForm表单验证
1.定义model.py model中定义的字段类型,只有在通过form进行验证的时候才有效,数据库中的字段类型与其并不完全一致,如数据库中并没有ipaddress类型.如果不通过form对字段进行验 ...
- django form 表单验证
随机推荐
- Jenkins快速上手安装
目录 环境准备 - JDK 安装 1. APT 安装 2. WAR包方式运行 3.Docker 方式运行 Jenkins 是一个独立的开源自动化服务器,可以用来自动化与构建.测试.交付或部署软件相关的 ...
- CF1511E Colorings and Dominoes
考虑计数拆开贡献. 因为在一个方案中一个格子最多只会贡献一次,那么不妨反过来求这个格子贡献了多少次. 然后发现,行列独立,那么我们单独计算红蓝色,即可. 一个偶数块贡献当且仅当前面也是偶数块. 然后显 ...
- 【基因组组装】HiC挂载Juicebox纠错补充
目录 1. 主要纠错类型 misjoins translocations inversions chromosome boundaries 2. 其他有用操作 撤销与反撤销 移到边角料 1. 主要纠错 ...
- [Linux] 非root安装GCC9.1.0
说明 一般Linux系统自带或公共的GCC版本都很低,如目前我们的服务器版本的GCC还停留在gcc-4.9.3,而官网已到达9.2版本(下载http://ftp.gnu.org/gnu/gcc/) , ...
- R shinydashboard ——1. 基本用法
shiny和shinydashboard使用虽然简单,但控件众多,需及时总结归纳. install.packages("shinydashboard") shinydashboar ...
- R语言与医学统计图形【3】条形图、误差图
R语言基础绘图系统 基础图形--条形图.误差图 3.条形图 barplot接收的数据是矩阵而非数据框. data <- sample(c(50:80),5) barplot(data,col=h ...
- Docker 外部访问容器Pp、数据管理volume、网络network 介绍
Docker 外部访问容器Pp.数据管理volume.网络network 介绍 外部访问容器 容器中可以运行一些网络应用,要让外部也可以访问这些应用,可以通过 -P 或 -p 参数来 指定端口映射. ...
- msql_5.6.46编译问题
初始化数据库的时候, 使用mysql_install_db 必须是再mysql安装的目录下用相对路径去进行初始化 CentOs6.9必须先把/etc/my.cnf 先改为其他名字,之后再把安装目录下s ...
- Shell 分发脚本
目录 Shell分发脚本 原理 rsync命令分析 特点 基本语法 实现 需求 环境变量 脚本实现 知识点 获得当前路径的目录dirname 获得当前路径的文件名basename shell远程执行命 ...
- 重学Git(一)
一.最最最基础操作 # 初始化仓库 git init # 添加文件到暂存区 git add readme.md # 提交 git commit -m 'wrote a readme file' 二.简 ...