day063 form 和modelform组件
注册功能: (写一个简单的注册功能,要求用户名长度不得小于6位.)
普通方式写注册功能
views视图下:
- def register(request):
- error_msg=' '
- if request.method=='GET':
- username=request.POST.get('name')
- password=request.POST.get('upwd')
- if len(username)<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视图如下:
首先我们先定义一个MyForm类:
- from django import forms
- class MyForm(forms.Form):
- name=forms.CharField( label='用户名:') #form字段的名称写的是什么,前段生成的input标签的时候,input标签的name就是什么
- upwd=forms.CharField( label='密码:') #label指的是在input标签前面加的文本内容
再写一个views视图函数:
- #基于form组件实现注册功能
- def register(request):
- #实例化一个form对象
- form_obj=RegForm()
- if request.method==' POST ':
- form_obj=RegForm(data=request.POST)
- #既然传过来的input标签的name属性值和form类对应的字段名是一样的,所以接过来后,form就取出对应的form字段名相同的数据进行form校验
- if form_obj.is_valid():
- return Httpresponse('注册成功!!')
- return render(request,'register.html',{ 'form_obj': form_obj })
login.html
- <!DOCTYPE html>
- <html lang="en">
- <head>
- <meta charset="UTF-8">
- <title>注册2</title>
- </head>
- <body>
- <form action="/reg2/" method="post" novalidate autocomplete="off"> #novalidate 告诉前端form表单,不要对输入的内容做校验
- {% csrf_token %}
- #{{ form_obj.as_p }} 直接写个这个,下面的用户名和密码的标签不自己写,你看看效果
- <div>
- <label for="{{ form_obj.name.id_for_label }}">{{ form_obj.name.label }}</label>
- {{ form_obj.name }} {{ form_obj.name.errors.0 }} #errors是这个字段所有的错误,我就用其中一个错误提示就可以了,再错了再提示,并且不是给你生成ul标签了,单纯的是错误文本
- {{ form_obj.errors }} #这是全局的所有错误,找对应字段的错误,就要form_obj.字段名
- </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.
插件:
initial : 初始值,input框里面的默认值(初始值).
- class loginform(forms.Form):
- username=forms.CharField(
- min_length=6, #最小长度
- max_length=10, #最大长度
- initial ='请输入用户名' , #设置默认值
- )
- password=forms.CharField(min_length=6,label='密码:')
error_messages : 重写错误信息.
- class loginform(forms.Form):
- username=forms.CharField(
- error_messages={
- 'required' : '不能为空',
- 'invalid' :'格式错误',
- 'min_length': '用户名最短为8位'
- }
- )
- pwd=forms.CharField(label='密码')
password :
- class loginform(forms.Form):
- ......
- pwd=forms.CharField(
- label='密码',
- widget=forms.widgets.PassowrdInput(attrs={'class':'c1'},render_value=True)
- )
radio Select
单选radio值为字符串
- class loginform(forms.Form):
- username=forms.CharField(
- min_length=8,
- ......
- )
- gender=forms.fields.ChoiceField(
- choices=((1,'男'),(2,'女'),(3,'嘻嘻嘻')),
- label='性别:',
- initial=-------,
- widget=forms.widgets.RadioSelect()
- )
单选select
- class loginform(forms.Form):
- hobby=forms.fields.ChoiceField(
- choices=((1,'篮球'),(2,'足球'),(3,'乒乓球')),
- label='爱好:',
- initial='------',
- )
多选select
- class loginform(forms.Form):
- ......
- hobby=forms.Fields.MultipleChoiceField(
- choices=((1,'篮球'),(2,'足球'),(3,'乒乓球')),
- label='爱好:',
- 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='爱好:',
- widget=forms.widgets.CheckboxSelectMultiple()
- )
form 所有内置字段
内置字段:
- field
- required=True, #是否允许为空
- widget=None, #HTML插件
- label='None', #用于生成label标签或者是显示内容(在input标签前面)
- 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:12
- DurationField(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.ModelChoiceField
- queryset, # 查询数据库中的数据
- empty_label="---------", # 默认空显示内容
- to_field_name=None, # HTML中value的值对应的字段
- limit_choices_to=None # ModelForm中对queryset二次筛选
- ModelMultipleChoiceField(ModelChoiceField)
- ... django.forms.models.ModelMultipleChoiceField
- TypedChoiceField(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=''
- GenericIPAddressField
- protocol='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类型
自定义验证函数
- 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'邮箱'}))
Hook钩子方法
局部钩子
我们在form类中定义clean_字段名()方法,就能够实现对特定字段进行校验
- class loginform(forms.Form):
- username=forms.CharField(
- min_length=5,
- label='用户名:',
- initial='默认值',
- error_messages={
- 'required': '不能为空',
- 'invalid': '格式错误',
- 'min_length':'用户名最短为8位'},
- widget=forms.widgets.TextInput(attrs={'class':'form-control'})
- )
- def clean_username(self):
- value=self.cleaned_data.get('username')
- if '666' in value:
- raise ValidationError('666翻了')
- else:
- return value
全局钩子
我们在form类中定义clean()方法,就能实现对字段进行全局校验,字段全部验证完毕,局部钩子也全部执行完毕之后,执行这个全局钩子校验.
- class loginform(forms.Form):
- ......
- password = forms.CharField(
- min_length=6,
- label="密码",
- widget=forms.widgets.PasswordInput(attrs={'class': 'form-control'}, render_value=True)
- )
- re_password = forms.CharField(
- min_length=6,
- label="确认密码",
- widget=forms.widgets.PasswordInput(attrs={'class': 'form-control'}, render_value=True)
- )
- ...
- # 定义全局的钩子,用来校验密码和确认密码字段是否相同,执行全局钩子的时候,cleaned_data里面肯定是有了通过前面验证的所有数据
- def clean(self):
- password_value = self.cleaned_data.get('password')
- re_password_value = self.cleaned_data.get('re_password')
- if password_value == re_password_value:
- return self.cleaned_data #全局钩子要返回所有的数据
- else:
- self.add_error('re_password', '两次密码不一致') #在re_password这个字段的错误列表中加上一个错误,并且clean_data里面会自动清除这个re_password的值,所以打印clean_data的时候会看不到它
- raise ValidationError('两次密码不一致')
modelform组件
- from django import forms
- class RbForms(forms.modelform):
- class Meta:
- model=models.Role
- fields='__all__'
- exclude=[xxx,xxx]
- widgets={
- 'name': forms.TextInput(attrs={'class': 'form-control'})
- }
- class BSForm(forms.ModelForm):
- def __init__(self, *args, **kwargs):
- super().__init__(*args, **kwargs)
- for field in self.fields.values():
- field.widget.attrs.update({"class": "form-control"})
在写别的具体的form的时候只需要继承这个BSForm就可以啦
- class HostForm(BSForm):
- class Meta:
- model = models.Host
- fields = "__all__"
- def clean_hostip(self):
- hostip = self.cleaned_data['hostip']
- host = models.Host.objects.filter(hostip=hostip)
- if host.count() == 0:
- return hostip
- elif host.count() != 0 and hostip == self.instance.hostip:
- return hostip
- else:
- raise forms.ValidationError("ip地址已存在,请重新输入.")
day063 form 和modelform组件的更多相关文章
- Django之Form、ModelForm 组件
Django之Form.ModelForm 组件 一.Form组件: django框架提供了一个form类,来处理web开发中的表单相关事项.众所周知,form最常做的是对用户输入的内容进行验证,为此 ...
- {Django基础十之Form和ModelForm组件}一 Form介绍 二 Form常用字段和插件 三 From所有内置字段 四 字段校验 五 Hook钩子方法 六 进阶补充 七 ModelForm
Django基础十之Form和ModelForm组件 本节目录 一 Form介绍 二 Form常用字段和插件 三 From所有内置字段 四 字段校验 五 Hook钩子方法 六 进阶补充 七 Model ...
- Django之Form与ModelForm组件
Django之Form与ModelForm组件 1.Form介绍 Form组件的主要功能如下: 生成页面可用的HTML标签 对用户提交的数据进行校验 O 保留上次的输入内容 普通方式手写注册功能 vi ...
- day 64 Django基础十之Form和ModelForm组件
Django基础十之Form和ModelForm组件 本节目录 一 Form介绍 二 Form常用字段和插件 三 From所有内置字段 四 字段校验 五 Hook钩子方法 六 进阶补充 七 Mod ...
- Django之 Form和ModelForm组件
01-Form介绍 我们之前在HTML页面中利用form表单向后端提交数据时,都会写一些获取用户输入的标签并且用form标签把它们包起来. 与此同时我们在好多场景下都需要对用户的输入做校验,比如校验用 ...
- Django Form和ModelForm组件
Form介绍 我们之前在HTML页面中利用form表单向后端提交数据时,都会写一些获取用户输入的标签并且用form标签把它们包起来. 与此同时我们在好多场景下都需要对用户的输入做校验,比如校验用户是否 ...
- Django基础十之Form和ModelForm组件
一 Form介绍 我们之前在HTML页面中利用form表单向后端提交数据时,都会写一些获取用户输入的标签并且用form标签把它们包起来. 与此同时我们在好多场景下都需要对用户的输入做校验,比如校验用户 ...
- Form和ModelForm组件
Form介绍 我们之前在HTML页面中利用form表单向后端提交数据时,都会写一些获取用户输入的标签并且用form标签把它们包起来. 与此同时我们在好多场景下都需要对用户的输入做校验,比如校验用户是否 ...
- 12.Django基础十之Form和ModelForm组件
一 Form介绍 我们之前在HTML页面中利用form表单向后端提交数据时,都会写一些获取用户输入的标签并且用form标签把它们包起来. 与此同时我们在好多场景下都需要对用户的输入做校验,比如校验用户 ...
随机推荐
- C# Tuple<T1,T2....T>元组的使用
1) 先说组元:一个数据结构,由通过逗号分割的,用于传递给一个程序或者操作系统的一系列值的组合. NET Framework 直接支持一至七元素的元组 Tuple<T1> Tuple< ...
- 测试Oracle统计信息的导出导入
背景:有时我们会希望可以对Oracle的统计信息整体进行导出导入.比如在数据库迁移前后,希望统计信息保持不变;又比如想对统计信息重新进行收集,但是担心重新收集的结果反而引发性能问题,想先保存当前的统计 ...
- appium元素获取
查看安卓手机的界面元素: 1.打开模拟器: 2.启动服务: 在cmd 输入: adb connect 127.0.0.1:62001 回车 可以输入 adb devices 查看启动状态 3.在a ...
- input[type = 'date']标签。
1.首先调用浏览器自带时间控件,input的type属性有以下几种写法: type=’date’ //显示年.月.日 type=‘month’//显示年.月 type=‘week’//显示年.周 ty ...
- visio studio删除空行
一.Ctrl+H 打开替换框 二.在替换框中的源中输入 ^(?([^\r\n])\s)*\r?$\r?\n
- nmon监控数据分析
性能测试中,各个服务器资源占用统计分析是一个很重要的组成部分,通常我们使用nmon这个工具来进行监控以及监控结果输出. 一. 在监控阶段使用类似下面的命令 ./nmon -f write_3s_20v ...
- Linux统计文件中单词出现的次数
grep -E "\b[[:alpha:]]+\b" /etc/fstab -o | sort | uniq -c 或 awk '{for(i=1;i<NF;i++){c ...
- Google advertiser api开发概述——入门指南
使用入门 AdWords API 可让应用直接与 AdWords 平台互动,大幅提高管理大型或复杂 AdWords 帐号和广告系列的效率.一些典型的用例包括: 自动帐号管理 自定义报告 基于产品目录的 ...
- C# ToLookup
下文参考翻译自: C#/.NET Little Wonders: The ToLookup() LINQ Extension Method 故事的背景 让我们先来创建一个简单的类来表示产品,产品有ID ...
- 激活Pychram
最近更新了Intellij IDEA到2018.1.5之后,使用之前的授权服务器(http://idea.imsxm.com)会提示Outdated License Server Detected,大 ...