单纯从前端的html
来说,表单是用来提交数据给服务器的,不管后台的服务器用的是Django还是PHP语言还是其他语言。只要input标签放在form标签中,然后再添加一个提交按钮,那么以后点击提交按钮,就可以将input标签对于的值提交给服务器了。
Django中的表单丰富了传统的HTML语言中的表单。在Django中的表单,主要做以下两件事:
在讲解Django表单的具体每部分的细节之前。我们首先先来看下整体的使用流程。首先我们在后台服务器定义一个表单类,继承于from django import froms
前面我们通过{{ from }}
模板语言,简单地将表单渲染到HTML页面中了,实际上,有更多的方式
{{ form.as_tabel}}
: 将表单渲染一个表格元素,每个输入框作为一个标签
{{ form.as_p }}
: 将表单的每个输入框包裹在一个
标签内tags
{{ form.as_ul }}
: 将表单渲染成一个列表元素,每个输入框作为一个
标签
froms
# @Time : 2020/7/15 13:01
# @Author : Small-J
# 继承Django的表单验证
from django import forms
class MessageBoardForm(forms.Form):
# 最大长度限制和最小长度限制
title = forms.CharField(max_length=100, min_length=2, label='标题')
content = forms.CharField(widget=forms.Textarea)
# 渲染表单的中文显示
email = forms.EmailField(label='邮箱')
# required
reply = forms.BooleanField(required=False)
index.html
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Titletitle>
head>
<body>
<h2>Form表单提交h2>
{# 对应的form标签 #}
<form action="" method="post">
<table>
{{ form.as_table }}
table>
<input type="submit" value="提交">
form>
body>
html>
常用的Field
使用Field可以是对数据验证的第一步。你期待这个提交上来的数据是什么类型,那么就使用什么类型的Field
。
CharField
用来接收文本。
参数:
max_length
: 这个字段值的最大长度。
min_length
: 这个字段值的最小长度。
required
: 这个字段是否必须的。默认是必须的。
error_messages
: 在某个条件验证失败的时候,给出错误信息。
EmailField
- 用来接收邮箱,会自动验证邮箱是否合法
- 错误信息的key :
required
、invalid
IntegerField
用来接收整形,并且验证通过后,会将这个字段的值转换为整形
max_value
: 最大的值
min_value
: 最小的值
- 错误信息的key:required 、invalid、max_value、min_value
IntegerField
用来接收整形,并且验证通过后,会将这个字段的值转换为整形
max_value
: 最大的值
min_value
: 最小的值
- 错误信息的key :
required
、 invalid
、max_value
、min_value
URLField
- 用来接收url格式的字符串
- 错误信息的key :
required
、invalid
forms.py
# @Time : 2020/7/19 14:21
# @Author : Small-J
from django import forms
class MyForm(forms.Form):
# 当我们输入一个错误的邮箱的时候,显示错误的信息
# {'email': [{'message': 'Enter a valid email address.', 'code': 'invalid'}]}
# 当显示错误的信息的时候会提示'Enter a vaild email address'
# 当我们想自定义错误信息的时候,可以在对应字段中写上参数error_messages
email = forms.EmailField(error_messages={'invalid': '请输入正确的邮箱地址'})
price = forms.FloatField(error_messages={'invalid': '请输入正确的浮点型数据'})
URL = forms.URLField(error_messages={'invalid': '请输入正确的邮箱地址', 'required': '请输入填写网站'})
views.py
from django.shortcuts import render
# 导入类视图
from django.views.generic import View
from .forms import MyForm
from django.http import HttpResponse
class IndexView(View):
def get(self, request):
return render(request, 'index.html')
def post(self, request):
form = MyForm(request.POST)
# 表示如果验证通过的话
if form.is_valid():
return HttpResponse('success')
else:
print(form.errors.get_json_data())
return HttpResponse('fail')
index.html
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Titletitle>
head>
<body>
<form action="" method="post">
邮箱:<input type="text" name="email"><br>
价格:<input type="text" name="price"><br>
URL:<input type="text" name="URL"><br>
<input type="submit" name="提交" >
form>
body>
html>
常用的验证器
在验证某个字段的时候,可以传递一个validators
参数用来指定验证器,进一步对数据进行过滤。验证器有很多,但是很多验证器我们其实已经通过这个Field或者一些参数就可以指定了。比如EmailValidator
,我们可以通过EmailFidle来指定,比如MaxValueValidator
,我们可以通过max_value
参数来指定。
MaxValueValidator
: 验证最大值
MinValueValidator
: 验证最小值
MinLengthVaidator
:验证最小长度
ManLengthVaidator
: 验证最大长度
EmailValidator
: 验证是否是邮箱格式
URLVaidator
: 验证是否为URL格式
RegexValidator
: 如果还需要更加复杂的验证,那么我们可以通过正则表达式验证
# 验证手机号码是否合法
# RegexValidator:代表着为正则表达式说法
# message :自定义错误信息显示
phone_number = forms.CharField(validators=[validators.RegexValidator(r'1[345678]\d{9}', message='请输入正确的手机号码')])
自定义的验证器
有时候对一个字段验证,不是一个长度,一个正则表达式能够写清楚的,还需要一些其他复杂的逻辑,那么我们可以对某个字段,进行自定义的验证。比如在注册的表单验证中,我们想要验证手机号码是否已经被注册过,那么这是就需要在数据库中进行判断才知道。对某个字段进行自定义的验证方式是,定义一个方法,这个方法的名字定义规则是:clean_fieldname。如果验证失败,那么就抛出一个验证错误。比如要验证用户表中手机号码之前是否在数据库中存在,那么可以通过以下代码实现
models.py
from django.db import models
# 模型
class MyForm(models.Model):
username = models.CharField(max_length=15)
telephone = models.CharField(max_length=11)
pwd1 = models.CharField(max_length=10, null=True)
pwd2 = models.CharField(max_length=10, null=True)
views.py
from django.shortcuts import render
# 导入类视图
from django.views.generic import View
from .forms import MyForm, RegisterForm
from django.http import HttpResponse
from .models import MyForm
class IndexView(View):
def get(self, request):
return render(request, 'index.html')
def post(self, request):
form = MyForm(request.POST)
# 表示如果验证通过的话
if form.is_valid():
return HttpResponse('success')
else:
print(form.errors.get_json_data())
return HttpResponse('fail')
class RegisterView(View):
def get(self, request):
return render(request, 'regist.html')
def post(self, request):
form = RegisterForm(request.POST)
# 验证表单数据是否存在
if form.is_valid():
# cleaned_data中的值类型与字段定义的Field类型一致
username = form.cleaned_data.get('username')
telephone = form.cleaned_data.get('telephone')
MyForm.objects.create(username=username, telephone=telephone)
return HttpResponse('success')
else:
print(form.errors.get_json_data())
return HttpResponse('fail')
regist.html
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Titletitle>
head>
<body>
<form action="" method="post">
<table>
<tr>
<td>用户名:td>
<td><input type="text" name="username">td>
tr>
<tr>
<td>手机号码:td>
<td><input type="text" name="telephone">td>
tr>
<tr>
<td>密码:td>
<td><input type="password" name="pwd1">td>
tr>
<tr>
<td>再次输入密码:td>
<td><input type="password" name="pwd2">td>
tr>
<tr>
<td>td>
<td><input type="submit" value="提交">td>
tr>
table>
form>
body>
html>
当针对某个字段的情况下
class RegisterForm(forms.Form):
username = forms.CharField(max_length=100)
# RegexValidator:正则表达式
telephone = forms.CharField(validators=[validators.RegexValidator(r'1[345678]\d{9}', message='请输入正确的手机号码')])
# clean+对应的字段名字 -针对某字段进行
# 该自定义的字段要返回数据
#
def clean_telephone(self):
telephone = self.cleaned_data.get('telephone')
# 进行数据库判断过滤
exists = MyForm.objects.filter(telephone=telephone).exists()
if exists:
# 判断数据是否存在,如果存在将主动抛出个异常
# ValidationError:验证失败的一个异常
raise forms.ValidationError(message='手机号码已存在')
return telephone
当针对多个字段的情况下
class RegisterForm(forms.Form):
username = forms.CharField(max_length=100)
# RegexValidator:正则表达式
telephone = forms.CharField(validators=[validators.RegexValidator(r'1[345678]\d{9}', message='请输入正确的手机号码')])
pwd1 = forms.CharField(max_length=16, min_length=6)
pwd2 = forms.CharField(max_length=16, min_length=6)
# clean+对应的字段名字 -针对某字段进行
# 该自定义的字段要返回数据
# 当针对多个字段的时候
def clean(self):
cleaned_data = super().clean()
pwd1 = cleaned_data.get('pwd1')
pwd2 = cleaned_data.get('pwd2')
if pwd1 != pwd2:
raise forms.ValidationError(message='两次输入的密码不一样')
return cleaned_data
提取错误信息
如果验证失败了,那么有一些错误信息是我们需要传给前端的。这时候我们可以通过以下属性来获取:
-
form.errors
: 这个属性获取的错误信息是一个包含了html标签的信息
-
form.errors.get_json_data()
: 这个方法获取的是一个字典类型的错误信息。将某个字段的名字作为key,错误信息作为值的一个字典。
-
form.as_json()
: 这个方法是将form.get_json_data()
返回的字典dump成json格式的字符串,方便进行传输。
-
上述方法获取的字段的错误值,都是一个比较复杂的数据。比如以下:
{'username': [{'message': 'Enter a valid URL.', 'code': 'invalid'}, {'message': 'Ensure this value has at most 4 characters (it has 22).', 'code': 'max_length'}]}
class MyForm(forms.Form):
username = forms.URLField(max_length=4)
def get_errors(self):
errors = self.errors.get_json_data()
new_errors = {}
for key,message_dicts in errors.items():
messages = []
for message in message_dicts:
messages.append(message['message'])
new_errors[key] = messages
return new_errors
你可能感兴趣的:(Django框架)