Django form表单

form介绍

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

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

django form组件就实现了上面所述的功能,总结一下, 其实form组件的主要功能如下:

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

 

普通方式手写注册功能

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>

views.py

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

 

使用form组件实现注册功能

先定义好一个RegForm类:

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

 

再写一个视图函数:

# 使用form组件实现注册方式
def register(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, "register.html", {"form_obj": form_obj})

 

再写前端登录页面:

login.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>注册</title>
</head>
<body>
   <form action="/register/" method = "POST" novalidate autocomplete = "off">
        {% csrf_token %}
        <div>
            <label for="{{ form_obj.username.id_for_label }}">
                {{ form_obj.usernaeme.label }}
            </label>
            {{form_obj.username}}
            {{form_obj.username.errors.0}}
        </div>
        <div>
            <label for="{{form_obj.password.id_for_label}}">
                {{ form_obj.password.label }}
            </label>
            {{ form_obj.password }}
            {{ form_obj.password.errors.0 }}
        </div>
        <div>
            <input type="submit" 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="张三" # 设置默认值
    )
    password = forms.CharField(min_length=6, label="密码")

 

error_messages

重写错误信息

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

 

password

class LoginForm(forms.Form):
    ...
    password = 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位"
        }
    )
     
    password = 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):
    ...
    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 fields
 
class MyForm(Form):
    user = fields.ChoiceField(
        initial = 2,
        widget = widgets.Select
    )
     
    def __init__(self, *args, **kwargs):
        super(MyForm, self).__init__(*args, **Kwargs)
        self.fields["user"].choices = models.Classes.object.all().value_list("id", "caption")

 

方法二:

from django import forms
from django.forms import fields
from django.forms import models as form_model
 
class FInfo(forms.Form):
    # 多选
    authors = form_model.ModelMultipleChoiceField(queryset=models.NNewType.objects.all())
     
    # 单选
    authors = form_model.ModelChoiceField(queryset=models.NNewType.objects.all())

 

发表评论