一、form大白话介绍

1.渲染标签

2.校验数据

3.渲染信息

  1. 1.渲染标签
  2. # 先产生一个空的类对象
  3. from_obj = MyRegFrom()
  4. # 将该对象传递给html页面 页面上借助与form_obj有三种渲染方式:详细见目录

二、普通方式手写注册功能

views.py

  1. # 注册
  2. def register(request):
  3. error_msg = ""
  4. if request.method == "POST":
  5. username = request.POST.get("name")
  6. pwd = request.POST.get("pwd")
  7. # 对注册信息做校验
  8. if len(username) < 6:
  9. # 用户长度小于6位
  10. error_msg = "用户名长度不能小于6位"
  11. else:
  12. # 将用户名和密码存到数据库
  13. return HttpResponse("注册成功")
  14. return render(request, "register.html", {"error_msg": error_msg})

register.html

  1. <!DOCTYPE html>
  2. <html lang="en">
  3. <head>
  4. <meta charset="UTF-8">
  5. <title>注册页面</title>
  6. </head>
  7. <body>
  8. <form action="/reg/" method="post">
  9. {% csrf_token %}
  10. <p>
  11. 用户名:
  12. <input type="text" name="name">
  13. </p>
  14. <p>
  15. 密码:
  16. <input type="password" name="pwd">
  17. </p>
  18. <p>
  19. <input type="submit" value="注册">
  20. <p style="color: red">{{ error_msg }}</p>
  21. </p>
  22. </form>
  23. </body>
  24. </html>

三、使用form组件实现注册功能

views.py

先定义好一个RegForm类:

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

再写一个视图函数:

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

register2.html

  1. <!DOCTYPE html>
  2. <html lang="en">
  3. <head>
  4. <meta charset="UTF-8">
  5. <title>注册2</title>
  6. </head>
  7. <body>
  8. <form action="/reg2/" method="post" novalidate autocomplete="off">
  9. {% csrf_token %}
  10. <div>
  11. <label for="{{ form_obj.name.id_for_label }}">{{ form_obj.name.label }}</label>
  12. {{ form_obj.name }} {{ form_obj.name.errors.0 }}
  13. </div>
  14. <div>
  15. <label for="{{ form_obj.pwd.id_for_label }}">{{ form_obj.pwd.label }}</label>
  16. {{ form_obj.pwd }} {{ form_obj.pwd.errors.0 }}
  17. </div>
  18. <div>
  19. <input type="submit" class="btn btn-success" value="注册">
  20. </div>
  21. </form>
  22. </body>
  23. </html>

看网页效果发现 也验证了form的功能:

• 前端页面是form类的对象生成的 -->生成HTML标签功能

• 当用户名和密码输入为空或输错之后 页面都会提示 -->用户提交校验功能

• 当用户输错之后 再次输入 上次的内容还保留在input框 -->保留上次输入内容

四、pycharm的专属测试环境

1.使用方法

  1. 1.导入要测试的py文件
  2. 2.生成一个对象

2.本地校验测试的一些参数

  1. from_obj.is_valid() //判断校验是否通过
  2. from_obj.cleaned_data //拿到当前符号校验的数据{'username': '111', 'password': '111'}
  3. form_obj.errors //拿到当前校验不通过的数据
  4. 少传参数Flalse,多传Trun。因为少传了拿不到校验的数据,多传了也不会使用。这是字典的形式

五、html渲染标签三种方式

forms组件只帮你渲染获取用户输入(输入 选择 下拉 文件)的标签 不渲染按钮和form表单标签

渲染出来的每一个input提示信息都是类中字段首字母大写

  1. class MyRegForm(forms.Form):
  2. username = forms.CharField(max_length=8, min_length=3) # 最长8位,最短3位
  3. password = forms.CharField(max_length=8, min_length=3) # 最长8位,最短3位
  4. email = forms.EmailField() # 邮箱验证
  5. def reg(request):
  6. # 1 先生成一个空的类对象
  7. form_obj = MyRegForm()
  8. if request.method == 'POST':
  9. # 3 获取用户数据并交给forms组件校验 request.POST
  10. form_obj = MyRegForm(request.POST)
  11. # 4 获取校验结果
  12. if form_obj.is_valid():
  13. return HttpResponse('数据没问题')
  14. else:
  15. # 5 获取校验失败的字段和提示信息
  16. print(form_obj.errors)
  17. # 2 直接将该对象传给前端页面
  18. return render(request, 'reg.html', locals())

第一种方式 {{ form_obj.as_p }} (不推荐)

不推荐,封装程度高,扩展性低。一般测试本地用

  1. <body>
  2. <p>第一种渲染方式:多个p标签 本地测试方便 封装程度太高了 不便于扩展</p>
  3. {{ form_obj.as_p }}
  4. {#{{ form_obj.as_ul }}#}
  5. {#{{ form_obj.as_table }}#}
  6. </body>

第二种方式 {{ form_obj.username }} (不推荐)

不推荐,扩展性较高 ,书写较为繁琐,每一个input框都需要自己手动写

  1. <p>第二种渲染方式: 扩展性较高 书写较为繁琐</p>
  2. <label for="{{ form_obj.username.id_for_label }}">{{ form_obj.username.label }}</label>
  3. {{ form_obj.username }}
  4. {{ form_obj.password.label }}{{ form_obj.password }}
  5. {{ form_obj.email.label }}{{ form_obj.email }}

第三种方式 for循环 (推荐)

推荐使用,for循环方式。也可以用ajax

{{ form.errors.0 }} # 这个是模板语法

  1. <p>第三种渲染方式 推荐使用</p>
  2. <form action="" method="post" novalidate>
  3. {% for form in form_obj %}
  4. <p>
  5. {{ form.label }}{{ form }}
  6. <span>{{ form.errors.0 }}</span>
  7. </p>
  8. {% endfor %}
  9. <input type="submit">
  10. </form>

六、校验数据

*******数据校验一个前后端都得有 但是前端的校验弱不禁风 可有可无

而后端的校验则必须非常全面

forms组件默认所有的字段必须传值,少传不行,多传的数据不做任何的处理

如何取消浏览器自动帮我们校验的功能?

在form后加参数 no validate,不验证

  1. form表单取消前端浏览器自动校验功能
  2. <form action="" method="post" novalidate>

常用校验参数

  1. max_length //允许输入的最大长度
  2. min_length //最小长度
  3. label input的提示信息,namepassword
  4. error_messages 自定义报错的提示信息
  5. 'max_length':"用户名最长8位",
  6. 'min_length':"用户名最短3位",
  7. 'required':"用户名不能为空"
  8. required 设置字段是否允许为空
  9. initial 设置默认值
  10. widget 控制type类型及属性 type classs
  11. validator 正则校验及报错信息,并且支持多个

使用方式

CharField用户名类型校验

  1. from django.forms import widgets //不导入也可以,没提示
  2. class MyRegForm(forms.Form):
  3. # 用户名最少3位最多8位
  4. username = forms.CharField(max_length=8,min_length=3,label='用户名',
  5. error_messages={ //报错信息的提示
  6. 'max_length':"用户名最长8位",
  7. 'min_length':"用户名最短3位",
  8. 'required':"用户名不能为空"
  9. },required=False,initial='jeff', // 为空和默认值
  10. widget=forms.widgets.TextInput(attrs={'class':'form-control c1 c2'}), //设置input的type属性为text,及class属性
  11. )

password校验

  1. class LoginForm(forms.Form):
  2. ...
  3. pwd = forms.CharField(
  4. min_length=6,
  5. label="密码",
  6. widget=forms.widgets.PasswordInput(attrs={'class': 'c1'}, render_value=True)
  7. )

邮箱类型校验

  1. class MyRegForm(forms.Form):
  2. # email字段必须填写符合邮箱格式的数据
  3. email = forms.EmailField(label='邮箱',error_messages={
  4. 'required':'邮箱必填',
  5. 'invalid':'邮箱格式不正确'
  6. })

手机号类型校验

正则匹配

  1. from django.core.validators import RegexValidator
  2. class MyRegForm(forms.Form):
  3. # 手机号
  4. phone = forms.CharField(
  5. validators=[
  6. RegexValidator(r'^[0-9]+$', '请输入数字'),
  7. RegexValidator(r'^159[0-9]+$', '数字必须以159开头')
  8. ]
  9. )

性别校验

  1. gender = forms.ChoiceField(
  2. choices=((1, "男"), (2, "女"), (3, "保密")),
  3. label="性别",
  4. initial=3,
  5. widget=forms.widgets.RadioSelect()
  6. )

爱好单选 select校验

  1. hobby = forms.ChoiceField(
  2. choices=((1, "篮球"), (2, "足球"), (3, "双色球"),),
  3. label="爱好",
  4. initial=3,
  5. widget=forms.widgets.Select() # 单选
  6. )

爱好多选select 校验1

  1. hobby1 = forms.MultipleChoiceField(
  2. choices=((1, "篮球"), (2, "足球"), (3, "双色球"),),
  3. label="爱好",
  4. initial=[1, 3],
  5. widget=forms.widgets.SelectMultiple()
  6. )

爱好多选chekbox校验2

  1. hobby2 = forms.MultipleChoiceField(
  2. choices=((1, "篮球"), (2, "足球"), (3, "双色球"),),
  3. label="爱好",
  4. initial=[1, 3],
  5. widget=forms.widgets.CheckboxSelectMultiple()
  6. )

是否记住密码校验

  1. keep = forms.ChoiceField(
  2. label="是否记住密码",
  3. initial="checked",
  4. widget=forms.widgets.CheckboxInput()
  5. )

七、钩子函数


  1. # 如果你想同时操作多个字段的数据你就用全局钩子
  2. # 如果你想操作单个字段的数据 你就用局部钩子
  3. 钩子勾回来处理完之后,还要还回去的

局部钩子

校验用户名中不能包含666

  1. # 局部钩子
  2. # 这里的self是自己类,MyRegForm
  3. def clean_username(self):
  4. username = self.cleaned_data.get('username')
  5. if '666' in username:
  6. self.add_error('username','光喊666是不行的') //添加报错信息
  7. return username //再把数据返回去

全局钩子

前面验证通过才走钩子函数验证。一层一层的验证

两次密码验证-----两个字段

  1. class MyRegForm(forms.Form):
  2. # 密码
  3. password = forms.CharField(max_length=8,min_length=3,label='密码',
  4. widget=forms.widgets.PasswordInput(attrs={'class':'form-control'})
  5. )
  6. # 密码验证
  7. re_password = forms.CharField(max_length=8,min_length=3,label='确认密码',
  8. widget=forms.widgets.PasswordInput(attrs={'class':'form-control'})
  9. )
  10. def clean(self):
  11. # 这里的self是自己类,MyRegForm
  12. # 校验密码和确认密码是否一致
  13. password = self.cleaned_data.get('password')
  14. re_password = self.cleaned_data.get('re_password')
  15. if not password == re_password:
  16. # 展示提示信息
  17. self.add_error('re_password','两次密码不一致') // 添加报错信息
  18. return self.cleaned_data

Django之form组件自动校验数据的更多相关文章

  1. django 使用form组件提交数据之form表单提交

    django的form组件可以减少后台在进行一些重复性的验证工作,极大降低开发效率. 最近遇到一个问题: 当使用form表单提交数据后,如果数据格式不符合后台定义的规则,需要重新在前端页面填写数据. ...

  2. Django之Form组件

    Django之Form组件 本节内容 基本使用 form中字段和插件 自定义验证规则 动态加载数据到form中 1. 基本使用 django中的Form组件有以下几个功能: 生成HTML标签 验证用户 ...

  3. Python之路【第二十一篇】:Django之Form组件

    Django之Form组件   Django的Form主要具有一下几大功能: 生成HTML标签 验证用户数据(显示错误信息) HTML Form提交保留上次提交数据 初始化页面显示内容 小试牛刀 1. ...

  4. 第十一篇:web之Django之Form组件

    Django之Form组件   Django之Form组件 本节内容 基本使用 form中字段和插件 自定义验证规则 动态加载数据到form中 1. 基本使用 django中的Form组件有以下几个功 ...

  5. python Django之Form组件

    python Django之Form组件 Django的Form主要具有一下几大功能: 生成HTML标签 验证用户数据(显示错误信息) HTML Form提交保留上次提交数据 初始化页面显示内容 小试 ...

  6. Django之Form组件(一)

    Django之Form组件(一) Django的Form主要具有一下几大功能: 生成HTML标签 验证用户数据(显示错误信息) HTML Form提交保留上次提交数据 初始化页面显示内容 基本操作:字 ...

  7. python框架之Django(10)-Form组件

    介绍 我们之前在HTML页面中利用form表单向后端提交数据时,都会写一些获取用户输入的标签并且用form标签把它们包起来.与此同时我们在好多场景下都需要对用户的输入做校验,比如校验用户是否输入,输入 ...

  8. 〖Python〗-- Django的Form组件

    [Django的Form组件] Django的Form主要具有一下几大功能: 生成HTML标签 验证用户数据(显示错误信息) HTML Form提交保留上次提交数据 初始化页面显示内容 Form类的使 ...

  9. Django之Form组件验证

    今天来谈谈Django的Form组件操作 Django中的Form一般有两种功能: ·输入html ·验证用户输入 Form验证流程 ·定义规则(是一个类)    ·前端把数据提交过来 ·匹配规则 · ...

随机推荐

  1. tf.contrib.layers.xavier_initializer

    https://blog.csdn.net/yinruiyang94/article/details/78354257xavier_initializer( uniform=True, seed=No ...

  2. [C++] WinAES的问题

    WinAES是个不错的windows CAPI封装. 如果C++程序需要和java的程序进行aes加解密通讯,那么WinAES的代码是有问题的. java的aes代码缺省不会设置IV而且采用ECB模式 ...

  3. Python--day60--一个简单(不完整)的web框架

  4. SpringBoot集成thymeleaf(自定义)模板中文乱码的解决办法

    楼主今天在学习SpringBoot集成thymelaf的时候报了中文乱码的错误,经过网上的搜索,现在得到解决的办法,分享给大家: package com.imooc.config; import or ...

  5. 2019-2-28-C#-16-进制字符串转-int-

    title author date CreateTime categories C# 16 进制字符串转 int lindexi 2019-02-28 11:51:36 +0800 2018-04-2 ...

  6. 分析JVM动态生成的类

    总结思考:让jvm创建动态类及其实例对象,需要给它提供哪些信息? 三个方面: 1.生成的类中有哪些方法,通过让其实现哪些接口的方式进行告知: 2.产生的类字节码必须有个一个关联的类加载器对象: 3.生 ...

  7. linux 原子变量

    有时, 一个共享资源是一个简单的整数值. 假设你的驱动维护一个共享变量 n_op, 它告 知有多少设备操作目前未完成. 正常地, 即便一个简单的操作例如: n_op++; 可能需要加锁. 某些处理器可 ...

  8. MySQL查询语句积累

    #查询名字中带李且名字是两个字的所有学生信息 SELECT * FROM user_test WHERE user_name LIKE '李_';

  9. 看到两道小学数学题,实在是解不动,用js写了一下

    把一个自然数的约数(除去它本身)按照从小到大的顺序写在它的左边,可以得到一个多位数,比如6的约数是1,2,3,写成一个多位数是1236,假如这个多位数中,没有直复数字,那么我们你这个多位数是唯一的.请 ...

  10. 2018.11.30 浪在ACM 集训队第七次测试赛

    https://blog.csdn.net/StilllFantasy/article/details/84670643 感谢刘凯同学 https://blog.csdn.net/UnKfrozen/ ...