Django form表单

Django form表单

Form介绍 

我们之前在HTML页面中利用form表单向后端提交数据时,都会写一些获取用户输入的标签并且用form标签把它们包起来。

与此同时我们在好多场景下都需要对用户的输入做校验,比如校验用户是否输入,输入的长度和格式等正不正确。如果用户输入的内容有错误就需要在页面上相应的位置显示对应的错误信息.。

Django form组件就实现了上面所述的功能。

总结一下,其实form组件的主要功能如下:

  • 生成页面可用的HTML标签
  • 对用户提交的数据进行校验
  • 保留上次输入内容
回到顶部

普通方式手写注册功能

views.py

复制代码
# 注册
def register(request):error_msg = ""if request.method == "POST":username = request.POST.get("name")pwd = request.POST.get("pwd")# 对注册信息做校验if len(username) < 6:# 用户长度小于6位error_msg = "用户名长度不能小于6位"else:# 将用户名和密码存到数据库return HttpResponse("注册成功")return render(request, "register.html", {"error_msg": error_msg})
复制代码

login.html

复制代码
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>注册页面</title>
</head>
<body>
<form action="/reg/" method="post">{% csrf_token %}<p>用户名:<input type="text" name="name"></p><p>密码:<input type="password" name="pwd"></p><p><input type="submit" value="注册"><p style="color: red">{{ error_msg }}</p></p>
</form>
</body>
</html>
复制代码
回到顶部

使用form组件实现注册功能

views.py

先定义好一个RegForm类:

from django import forms# 按照Django form组件的要求自己写一个类
class RegForm(forms.Form):name = forms.CharField(label="用户名")pwd = forms.CharField(label="密码")

再写一个视图函数:

复制代码
# 使用form组件实现注册方式
def register2(request):form_obj = RegForm()if request.method == "POST":# 实例化form对象的时候,把post提交过来的数据直接传进去form_obj = RegForm(request.POST)# 调用form_obj校验数据的方法if form_obj.is_valid():return HttpResponse("注册成功")return render(request, "register2.html", {"form_obj": form_obj})
复制代码

login2.html

复制代码
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>注册2</title>
</head>
<body><form action="/reg2/" method="post" novalidate autocomplete="off">{% csrf_token %}<div><label for="{{ form_obj.name.id_for_label }}">{{ form_obj.name.label }}</label>{{ form_obj.name }} {{ form_obj.name.errors.0 }}</div><div><label for="{{ form_obj.pwd.id_for_label }}">{{ form_obj.pwd.label }}</label>{{ form_obj.pwd }} {{ form_obj.pwd.errors.0 }}</div><div><input type="submit" class="btn btn-success" value="注册"></div></form>
</body>
</html>
复制代码

看网页效果发现 也验证了form的功能:
• 前端页面是form类的对象生成的                                      -->生成HTML标签功能
• 当用户名和密码输入为空或输错之后 页面都会提示        -->用户提交校验功能
• 当用户输错之后 再次输入 上次的内容还保留在input框   -->保留上次输入内容

Form那些事儿

回到顶部

常用字段与插件

创建Form类时,主要涉及到 【字段】 和 【插件】,字段用于对用户请求数据的验证,插件用于自动生成HTML;

initial

初始值,input框里面的初始值。

复制代码
class LoginForm(forms.Form):username = forms.CharField(min_length=8,label="用户名",initial="张三"  # 设置默认值
    )pwd = forms.CharField(min_length=6, label="密码")
复制代码

error_messages

重写错误信息。

复制代码
class LoginForm(forms.Form):username = forms.CharField(min_length=8,label="用户名",initial="张三",error_messages={"required": "不能为空","invalid": "格式错误","min_length": "用户名最短8位"})pwd = forms.CharField(min_length=6, label="密码")
复制代码

password

复制代码
class LoginForm(forms.Form):...pwd = forms.CharField(min_length=6,label="密码",widget=forms.widgets.PasswordInput(attrs={'class': 'c1'}, render_value=True))
复制代码

radioSelect

单radio值为字符串

复制代码
class LoginForm(forms.Form):username = forms.CharField(min_length=8,label="用户名",initial="张三",error_messages={"required": "不能为空","invalid": "格式错误","min_length": "用户名最短8位"})pwd = forms.CharField(min_length=6, label="密码")gender = forms.fields.ChoiceField(choices=((1, ""), (2, ""), (3, "保密")),label="性别",initial=3,widget=forms.widgets.RadioSelect())
复制代码

单选Select

复制代码
class LoginForm(forms.Form):...hobby = forms.fields.ChoiceField(choices=((1, "篮球"), (2, "足球"), (3, "双色球"), ),label="爱好",initial=3,widget=forms.widgets.Select())
复制代码

多选Select

复制代码
class LoginForm(forms.Form):...hobby = forms.fields.MultipleChoiceField(choices=((1, "篮球"), (2, "足球"), (3, "双色球"), ),label="爱好",initial=[1, 3],widget=forms.widgets.SelectMultiple())
复制代码

单选checkbox

复制代码
class LoginForm(forms.Form):...keep = forms.fields.ChoiceField(label="是否记住密码",initial="checked",widget=forms.widgets.CheckboxInput())
复制代码

多选checkbox

复制代码
class LoginForm(forms.Form):...hobby = forms.fields.MultipleChoiceField(choices=((1, "篮球"), (2, "足球"), (3, "双色球"),),label="爱好",initial=[1, 3],widget=forms.widgets.CheckboxSelectMultiple())
复制代码

关于choice的注意事项:

在使用选择标签时,需要注意choices的选项可以从数据库中获取,但是由于是静态字段 ***获取的值无法实时更新***,那么需要自定义构造方法从而达到此目的。

方式一:

复制代码
from django.forms import Form
from django.forms import widgets
from django.forms import fieldsclass MyForm(Form):user = fields.ChoiceField(# choices=((1, '上海'), (2, '北京'),),initial=2,widget=widgets.Select)def __init__(self, *args, **kwargs):super(MyForm,self).__init__(*args, **kwargs)# self.fields['user'].choices = ((1, '上海'), (2, '北京'),)#self.fields['user'].choices = models.Classes.objects.all().values_list('id','caption')
复制代码

方式二:

复制代码
from django import forms
from django.forms import fields
from django.forms import models as form_modelclass FInfo(forms.Form):authors = form_model.ModelMultipleChoiceField(queryset=models.NNewType.objects.all())  # 多选# authors = form_model.ModelChoiceField(queryset=models.NNewType.objects.all())  # 单选
复制代码
回到顶部

Django Form所有内置字段

Fieldrequired=True,               是否允许为空widget=None,                 HTML插件label=None,                  用于生成Label标签或显示内容initial=None,                初始值help_text='',                帮助信息(在标签旁边显示)error_messages=None,         错误信息 {'required': '不能为空', 'invalid': '格式错误'}validators=[],               自定义验证规则localize=False,              是否支持本地化disabled=False,              是否可以编辑label_suffix=None            Label内容后缀CharField(Field)max_length=None,             最大长度min_length=None,             最小长度strip=True                   是否移除用户输入空白IntegerField(Field)max_value=None,              最大值min_value=None,              最小值FloatField(IntegerField)...DecimalField(IntegerField)max_value=None,              最大值min_value=None,              最小值max_digits=None,             总长度decimal_places=None,         小数位长度BaseTemporalField(Field)input_formats=None          时间格式化   DateField(BaseTemporalField)    格式:2015-09-01
TimeField(BaseTemporalField)    格式:11:12
DateTimeField(BaseTemporalField)格式:2015-09-01 11:12DurationField(Field)            时间间隔:%d %H:%M:%S.%f...RegexField(CharField)regex,                      自定制正则表达式max_length=None,            最大长度min_length=None,            最小长度error_message=None,         忽略,错误信息使用 error_messages={'invalid': '...'}EmailField(CharField)      ...FileField(Field)allow_empty_file=False     是否允许空文件ImageField(FileField)      ...注:需要PIL模块,pip3 install Pillow以上两个字典使用时,需要注意两点:- form表单中 enctype="multipart/form-data"- view函数中 obj = MyForm(request.POST, request.FILES)URLField(Field)...BooleanField(Field)  ...NullBooleanField(BooleanField)...ChoiceField(Field)...choices=(),                选项,如:choices = ((0,'上海'),(1,'北京'),)required=True,             是否必填widget=None,               插件,默认select插件label=None,                Label内容initial=None,              初始值help_text='',              帮助提示ModelChoiceField(ChoiceField)...                        django.forms.models.ModelChoiceFieldqueryset,                  # 查询数据库中的数据empty_label="---------",   # 默认空显示内容to_field_name=None,        # HTML中value的值对应的字段limit_choices_to=None      # ModelForm中对queryset二次筛选ModelMultipleChoiceField(ModelChoiceField)...                        django.forms.models.ModelMultipleChoiceFieldTypedChoiceField(ChoiceField)coerce = lambda val: val   对选中的值进行一次转换empty_value= ''            空值的默认值MultipleChoiceField(ChoiceField)...TypedMultipleChoiceField(MultipleChoiceField)coerce = lambda val: val   对选中的每一个值进行一次转换empty_value= ''            空值的默认值ComboField(Field)fields=()                  使用多个验证,如下:即验证最大长度20,又验证邮箱格式fields.ComboField(fields=[fields.CharField(max_length=20), fields.EmailField(),])MultiValueField(Field)PS: 抽象类,子类中可以实现聚合多个字典去匹配一个值,要配合MultiWidget使用SplitDateTimeField(MultiValueField)input_date_formats=None,   格式列表:['%Y--%m--%d', '%m%d/%Y', '%m/%d/%y']input_time_formats=None    格式列表:['%H:%M:%S', '%H:%M:%S.%f', '%H:%M']FilePathField(ChoiceField)     文件选项,目录下文件显示在页面中path,                      文件夹路径match=None,                正则匹配recursive=False,           递归下面的文件夹allow_files=True,          允许文件allow_folders=False,       允许文件夹required=True,widget=None,label=None,initial=None,help_text=''GenericIPAddressFieldprotocol='both',           both,ipv4,ipv6支持的IP格式unpack_ipv4=False          解析ipv4地址,如果是::ffff:192.0.2.1时候,可解析为192.0.2.1, PS:protocol必须为both才能启用SlugField(CharField)           数字,字母,下划线,减号(连字符)...UUIDField(CharField)           uuid类型
Django Form内置字段
回到顶部

校验

方式一:

复制代码
from django.forms import Form
from django.forms import widgets
from django.forms import fields
from django.core.validators import RegexValidatorclass MyForm(Form):user = fields.CharField(validators=[RegexValidator(r'^[0-9]+$', '请输入数字'), RegexValidator(r'^159[0-9]+$', '数字必须以159开头')],)
复制代码

方式二:

复制代码
import re
from django.forms import Form
from django.forms import widgets
from django.forms import fields
from django.core.exceptions import ValidationError# 自定义验证规则
def mobile_validate(value):mobile_re = re.compile(r'^(13[0-9]|15[012356789]|17[678]|18[0-9]|14[57])[0-9]{8}$')if not mobile_re.match(value):raise ValidationError('手机号码格式错误')class PublishForm(Form):title = fields.CharField(max_length=20,min_length=5,error_messages={'required': '标题不能为空','min_length': '标题最少为5个字符','max_length': '标题最多为20个字符'},widget=widgets.TextInput(attrs={'class': "form-control",'placeholder': '标题5-20个字符'}))# 使用自定义验证规则phone = fields.CharField(validators=[mobile_validate, ],error_messages={'required': '手机不能为空'},widget=widgets.TextInput(attrs={'class': "form-control",'placeholder': u'手机号码'}))email = fields.EmailField(required=False,error_messages={'required': u'邮箱不能为空','invalid': u'邮箱格式错误'},widget=widgets.TextInput(attrs={'class': "form-control", 'placeholder': u'邮箱'}))
复制代码
回到顶部

补充进阶

应用Bootstrap样式

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta http-equiv="x-ua-compatible" content="IE=edge"><meta name="viewport" content="width=device-width, initial-scale=1"><link rel="stylesheet" href="/static/bootstrap/css/bootstrap.min.css"><title>login</title>
</head>
<body>
<div class="container"><div class="row"><form action="/login2/" method="post" novalidate class="form-horizontal">{% csrf_token %}<div class="form-group"><label for="{{ form_obj.username.id_for_label }}"class="col-md-2 control-label">{{ form_obj.username.label }}</label><div class="col-md-10">{{ form_obj.username }}<span class="help-block">{{ form_obj.username.errors.0 }}</span></div></div><div class="form-group"><label for="{{ form_obj.pwd.id_for_label }}" class="col-md-2 control-label">{{ form_obj.pwd.label }}</label><div class="col-md-10">{{ form_obj.pwd }}<span class="help-block">{{ form_obj.pwd.errors.0 }}</span></div></div><div class="form-group"><label class="col-md-2 control-label">{{ form_obj.gender.label }}</label><div class="col-md-10"><div class="radio">{% for radio in form_obj.gender %}<label for="{{ radio.id_for_label }}">{{ radio.tag }}{{ radio.choice_label }}</label>{% endfor %}</div></div></div><div class="form-group"><div class="col-md-offset-2 col-md-10"><button type="submit" class="btn btn-default">注册</button></div></div></form></div>
</div><script src="/static/jquery-3.2.1.min.js"></script>
<script src="/static/bootstrap/js/bootstrap.min.js"></script>
</body>
</html>
Django form应用Bootstrap样式简单示例

批量添加样式

可通过重写form类的init方法来实现。

class LoginForm(forms.Form):username = forms.CharField(min_length=8,label="用户名",initial="张三",error_messages={"required": "不能为空","invalid": "格式错误","min_length": "用户名最短8位"}...def __init__(self, *args, **kwargs):super(LoginForm, self).__init__(*args, **kwargs)for field in iter(self.fields):self.fields[field].widget.attrs.update({'class': 'form-control'})
批量添加样式

ModelForm

form与model的终极结合。

复制代码
class BookForm(forms.ModelForm):class Meta:model = models.Bookfields = "__all__"labels = {"title": "书名","price": "价格"}widgets = {"password": forms.widgets.PasswordInput(attrs={"class": "c1"}),}
复制代码

 class Meta:下常用参数:

复制代码
model = models.Student  # 对应的Model中的类
fields = "__all__"  # 字段,如果是__all__,就是表示列出所有的字段
exclude = None  # 排除的字段
labels = None  # 提示信息
help_texts = None  # 帮助提示信息
widgets = None  # 自定义插件
error_messages = None  # 自定义错误信息
复制代码

转载于:https://www.cnblogs.com/chenyibai/p/9807131.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/279159.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

java 多线程 优先级_java多线程之线程的优先级

在操作系统中&#xff0c;线程可以划分优先级&#xff0c;优先级较高的线程得到CPU资源较多&#xff0c;也就是CPU优先执行优先级较高的线程对象中的任务(其实并不是这样)。在java中&#xff0c;线程的优先级用setPriority()方法就行&#xff0c;线程的优先级分为1-10这10个等级…

PyQt5应用与实践

2015-01-16 19:00 by 吴秦, 69476 阅读, 5 评论, 收藏, 编辑 一个典型的GUI应用程序可以抽象为&#xff1a;主界面&#xff08;菜单栏、工具栏、状态栏、内容区域&#xff09;&#xff0c;二级界面&#xff08;模态、非模态&#xff09;&#xff0c;信息提示&#xff08;Toolti…

plex实现流媒体服务器_Plex继续远离服务器,提供网络节目

plex实现流媒体服务器() Plex now offers a “Web Shows” feature in certain versions of their interface, providing access to shows from brands like TWiT, GQ, and Popular Science. Plex现在在其界面的某些版本中提供了“网络节目”功能&#xff0c;可以访问TWiT&…

MIME协议(三) -- MIME邮件的组织结构

一封MIME邮件可以由多个不同类型的MIME消息组合而成&#xff0c;一个MIME消息表示邮件中的一个基本MIME资源或若干基本MIME消息的组合体。每个MIME消息的数据格式与RFC822数据格式相似&#xff0c;也包括头和体两部分&#xff0c;分别称为MIME消息头和MIME消息体&#xff0c;它…

discord linux_最好的Discord机器人来启动服务器

discord linuxDiscord has an extensive API and good support for bots on their platform. Because of this, there are tons of bots to go around. However, many of them just copy one another’s functionality. We’ve picked out the ones that do it right, and comp…

2019年4月第四周_2012年4月最佳怪胎文章

2019年4月第四周This past month we covered topics such as how to use a 64-bit web browser on Windows, the best tips and tweaks for getting the most out of Firefox, how to check out library books on your Kindle for free, and more. Join us as we look back at …

物体成瘾性_科技成瘾使我们不那么快乐。 那是一个市场机会。

物体成瘾性Compulsively checking social networks makes us less happy. I think we all understand this intuitively, the same way we understand that working out more and eating better is a good idea. 强迫检查社交网络使我们不那么开心。 我认为我们所有人都可以凭直…

装饰设计模式和例题

文件复制程序&#xff1a; 将一个文件复制一份出来&#xff0c;实现方法很简单&#xff0c;使用FileInputStream读取文件内容&#xff0c;然后使用FileOutputStream写入另一个文件&#xff0c;利用read方法的返回值作为while循环的条件&#xff0c;进行一边读一边写。 代码示例…

mysql操作手册我_MySQL使用指南一

我将MySQL常用指令整理出来分享给大家。1. 列出所有数据库mysql> show databases;2. 创建数据库mysql> create databases MyStorage;3. 打开数据库mysql> use MyStorage;4. 创建表mysql> create table Storage-> (-> id int,-> name varchar(50),-> pr…

谷歌地图将很快显示电动汽车充电站

If you’re out on the road in the future and find your electric vehicle is in dire need of a charge, you’ll soon be able to look to Google Maps for help finding a charging station. 如果您将来出门在外&#xff0c;并且发现您的电动汽车急需充电&#xff0c;那么…

JS4

1. js的本质就是处理数据。数据来自于后台的数据库。 所以变量就起到一个临时存储数据的作用。 ECMAScript制定了js的数据类型。 数据类型有哪些&#xff1f; 字符串 String数字 Number布尔 BooleanNull 空Undefined Object 对象Array 数组 json function …

松弛变量可以为负吗_如何为松弛安装(非官方)暗模式

松弛变量可以为负吗Slack still doesn’t have a dark mode. They have dark themes, but those only let you customize the sidebar colors, leaving the main window white. With the release of system-wide dark modes on macOS Mojave and Windows 10, Slack feels very …

如何在Mac上设置FaceTime

FaceTime is Apple’s built-in video and audio calling app. It pairs with your iPhone and allows you to make phone calls on macOS. FaceTime是Apple的内置视频和音频通话应用程序。 它可以与iPhone配对使用&#xff0c;并允许您在macOS上拨打电话。 You don’t need an…

在Ubuntu 11.10中将窗口按钮移回右侧

As of Ubuntu 10.04, the minimize, maximize, and close buttons on all windows were moved to the left side and the system menu was removed. Prior to version 11.10, you could use several methods to restore the original button arrangement. 从Ubuntu 10.04开始&a…

如何在Windows 10上使用触摸板手势

If you’ve used a touchpad in Windows 10, you’re no doubt aware of the basic single-finger tapping and two-finger scrolling gestures. Windows 10 also packs in some additional gestures you might not have tried. 如果您在Windows 10中使用了触摸板&#xff0c;那…

相机模拟光圈_我的相机应该使用什么光圈?

相机模拟光圈Aperture, along with shutter speed and ISO, is one of the three most important settings you control when you take a photo. It affects both the amount of light that hits your camera sensor and the depth of field of your images. Let’s look at ho…

2018-2019-1 20165234 《信息安全系统设计基础》第四周学习总结

一、学习目标 了解ISA抽象的作用 掌握ISA&#xff0c;并能举一反三学习其他体系结构 了解流水线和实现方式二、学习内容 Y86-64指令 movq指令 irmovq rrmovq mrmovq rmmovq四个整数操指令 addq,subq,andq,xorq只对寄存器数据进行操作7个跳转指令 cmovle cmovl cmove cmovne cmo…

Python之钉钉机器人推送天气预报

通过Python脚本结合钉钉机器人&#xff0c;定时向钉钉群推送天气预报 #!/usr/bin/python # -*- coding: utf-8 -*- # Author: aikergdedu.ml # My blog http://m51cto.51cto.blog.com import requests import re import urllib2 import json import sys import osheaders {Co…

google +按钮_如何禁用或改善Google的Google+集成

google 按钮If you’ve used Google lately, you’ve probably seen Google taking over Google’s search results. You don’t have to put up with it — you can disable the integration, show better social-networking pages or hide those pesky Google notifications.…

java 集合读写同步_JAVA多线程学习十六 - 同步集合类的应用

1.引言在多线程的环境中&#xff0c;如果想要使用容器类&#xff0c;就需要注意所使用的容器类是否是线程安全的。在最早开始&#xff0c;人们一般都在使用同步容器(Vector,HashTable),其基本的原理&#xff0c;就是针对容器的每一个操作&#xff0c;都添加synchronized来进行同…