表单-django

ぃ、小莉子 提交于 2019-11-27 17:16:02

#表单-django
@(python)

  • URL相关信息
    HttpRequest对象包含当前请求URL的一些信息:
    | 属性/方法 | 说明 | 举例 |
    | :-------- |: --------| :--: |
    |request.path |除域名以外的请求路径,以正斜杠开头 |"/hello/"|
    |request.get_host()| 主机名(比如,通常所说的域名)| "127.0.0.1:8000" or "www.example.com"|
    |request.get_full_path() |请求路径,可能包含查询字符串 |"/hello/?print=true"|
    |request.is_secure()| 如果通过HTTPS访问,则此方法返回True, 否则返回False| True 或者 False|
  • 简单例子
    在users app下views.py,添加一下代码
from django.http import HttpResponse
def search_form(request):
    return render_to_response('search_form.html')
def search(request):
    if 'name' in request.GET:
        try:
            info = Info.objects.get(name=request.GET['name']);
        except Info.DoesNotExist:
            message = 'no query'
        else:
            message = 'You searched for: %s %s %s' % (info.name,info.sex,info.email)
    else:
        message = 'You submitted an empty form.'
    return HttpResponse(message)

同时新建模版文件search_form.html

<!--search_form.html-->
<html>
<head>
    <title>Search</title>
</head>
<body>
    <form action="/search/" method="get">
        name:<input type="text" name="name">
        <input type="submit" value="Search">
    </form>
</body>
</html>

在urls.py添加一下规则

    url(r'^search_form/$', 'users.views.search_form'),
    url(r'^search/$', 'users.views.search'),

打开浏览器http://ip:8000/search_form/,就会看到一下界面

  • django.form
    在app中新建form.py,构建表单属性,这个不一定单独构建form.py文件,可以放到任何地方,甚至写入views.py中。
#form.py
#coding=utf-8
#forms.py
from django import forms
class UsersForm(forms.Form):
        name = forms.CharField(max_length=30)
        sex = forms.CharField(max_length=6)
        age = forms.IntegerField()
        email = forms.EmailField(required=False)

在views.py添加一下代码

from users.forms import UsersForm
from django.views.decorators.csrf import csrf_exempt
@csrf_exempt
def show_form(request):
    if request.method == 'POST':
        form = UsersForm(request.POST)
        if form.is_valid():
             cd = form.cleaned_data
             message = 'You searched for: %s %s %s' % (cd['name'],cd['sex'],cd['email'])
             return HttpResponse(message)
            #return HttpResponseRedirect('/contact/thanks/')
    else:
        form = UsersForm(initial={'email': '@'})
    return render_to_response('users_form.html', {'form': form})

新建模版文件users_form.html

<html>
<head>
    <title>Show User</title>
</head>
<body>
    <h1>Show User</h1>

    {% if form.errors %}
        <p style="color: red;">
            Please correct the error{{ form.errors|pluralize }} below.
        </p>
    {% endif %}
    <form action="" method="post">
        <table>
            {{ form.as_table }}
        </table>
        <input type="submit" value="Submit">
    </form>
</body>
</html>

此时打开浏览器http://ip:8000/show_form/,会看到如下界面

如果没有添加from django.views.decorators.csrf import csrf_exempt,与修饰符@csrf_exempt,就会出现在post提交表单时会出现CSRF token missing or incorrect错误。开启django.middleware.csrf.CsrfViewMiddleware中间件后,在post提交表单时会出现CSRF token missing or incorrect错误。首先说明csrf中间件是django框架提供的阻止跨站伪造请求攻击(Cross Site Request Forgery)的一个实现。
form的initial参数是表单的默认值,如form = UsersForm(initial={'email': '@'})是email的默认值是@.

  • 自定义校验规则
    django可以允许自定义对提交的表单进行校验,先看看下面的例子
#coding=utf-8
#forms.py
from django import forms
class UsersForm(forms.Form):
        name = forms.CharField(max_length=30)
        sex = forms.CharField(max_length=6)
        age = forms.IntegerField()
        email = forms.EmailField(required=False)
        def clean_sex(self):
            sex = self.cleaned_data['sex']
            if sex not in ['male','female']:
                raise forms.ValidationError("sex item error")
            return sex

Django的form系统自动寻找匹配的函数方法,该方法名称以clean_开头,并以字段名称结束。 特别地,clean_sex()方法将在指定字段的默认校验逻辑执行之后被调用。如果有这样的方法,它将在校验时被调用。例子中的clean_sex是对sex字段进行校验,使用cleaned_data提取表单值.

  • 指定标签
    <label>标签为 input 元素定义标注(标记)。
    label 元素不会向用户呈现任何特殊效果。不过,它为鼠标用户改进了可用性。如果您在 label 元素内点击文本,就会触发此控件。就是说,当用户选择该标签时,浏览器就会自动将焦点转到和标签相关的表单控件上。
<form>
  <label for="male">Male</label>
  <input type="radio" name="sex" id="male" />
  <br />
  <label for="female">Female</label>
  <input type="radio" name="sex" id="female" />
</form>
class UsersForm(forms.Form):
        name = forms.CharField(max_length=30)
        sex = forms.CharField(max_length=6)
        age = forms.IntegerField()
        email = forms.EmailField(required=False,label='Your e-mail address')

把该form打印出来,此时email没有添加label='Your e-mail address',

>>> from users.forms import UsersForm
>>> f = UsersForm
>>> print f
<class 'users.forms.UsersForm'>
>>> f = UsersForm()
>>> print f
<tr><th><label for="id_name">Name:</label></th><td><input id="id_name" maxlength="30" name="name" type="text" /></td></tr>
<tr><th><label for="id_sex">Sex:</label></th><td><input id="id_sex" maxlength="6" name="sex" type="text" /></td></tr>
<tr><th><label for="id_age">Age:</label></th><td><input id="id_age" name="age" type="number" /></td></tr>
<tr><th><label for="id_email">Email:</label></th><td><input id="id_email" name="email" type="email" /></td></tr>
>>> 

添加label后,email的label变为<label for="id_email">Your e-mail address:</label>

>>> from users.forms import UsersForm
>>> f = UsersForm()
>>> print f
<tr><th><label for="id_name">Name:</label></th><td><input id="id_name" maxlength="30" name="name" type="text" /></td></tr>
<tr><th><label for="id_sex">Sex:</label></th><td><input id="id_sex" maxlength="6" name="sex" type="text" /></td></tr>
<tr><th><label for="id_age">Age:</label></th><td><input id="id_age" name="age" type="number" /></td></tr>
<tr><th><label for="id_email">Your e-mail address:</label></th><td><input id="id_email" name="email" type="email" /></td></tr>
>>> 

如果点击email项,则会显示"Your e-mail address"。

  • 控制label和id
    可以使用auto_id变量控制label和id ,auto_id必须为True、False或字符串。
>>> f = UsersForm(auto_id=False)#省略了id和label
>>> print f
<tr><th>Name:</th><td><input maxlength="30" name="name" type="text" /></td></tr>
<tr><th>Sex:</th><td><input maxlength="6" name="sex" type="text" /></td></tr>
<tr><th>Age:</th><td><input name="age" type="number" /></td></tr>
<tr><th>Your e-mail address:</th><td><input name="email" type="email" /></td></tr>
>>> 

如果auto_id = True 则会自动使用label,且id名称为它们的字段名

>>> f = UsersForm(auto_id=True)
>>> print f
<tr><th><label for="name">Name:</label></th><td><input id="name" maxlength="30" name="name" type="text" /></td></tr>
<tr><th><label for="sex">Sex:</label></th><td><input id="sex" maxlength="6" name="sex" type="text" /></td></tr>
<tr><th><label for="age">Age:</label></th><td><input id="age" name="age" type="number" /></td></tr>
<tr><th><label for="email">Your e-mail address:</label></th><td><input id="email" name="email" type="email" /></td></tr>
>>> 

auto_id使用格式化字符串(%s)

>>> f = UsersForm(auto_id='id_for_%s')
>>> print f
<tr><th><label for="id_for_name">Name:</label></th><td><input id="id_for_name" maxlength="30" name="name" type="text" /></td></tr>
<tr><th><label for="id_for_sex">Sex:</label></th><td><input id="id_for_sex" maxlength="6" name="sex" type="text" /></td></tr>
<tr><th><label for="id_for_age">Age:</label></th><td><input id="id_for_age" name="age" type="number" /></td></tr>
<tr><th><label for="id_for_email">Your e-mail address:</label></th><td><input id="id_for_email" name="email" type="email" /></td></tr>
>>> 

通过上面我们知道,默认的auto_id使用格式化字符串 auto_id = 'id_%s'
接下来控制Label后缀,通过label_suffix 进行控制

>>> f = UsersForm(label_suffix='_form')
>>> print f
<tr><th><label for="id_name">Name_form</label></th><td><input id="id_name" maxlength="30" name="name" type="text" /></td></tr>
<tr><th><label for="id_sex">Sex_form</label></th><td><input id="id_sex" maxlength="6" name="sex" type="text" /></td></tr>
<tr><th><label for="id_age">Age_form</label></th><td><input id="id_age" name="age" type="number" /></td></tr>
<tr><th><label for="id_email">Your e-mail address_form</label></th><td><input id="id_email" name="email" type="email" /></td></tr>
>>> 
  • 自定义验证样式类
    如果验证不通过,则会输出错误,对应的有“必需”、‘错误’两项,那么就在这两项中做文章。
    添加一下代码,表格添加相应的css class。
        error_css_class = 'error'#当提示错误的时候,使用的是error类
        required_css_class = 'required'#当提示必须的时候,使用required
#coding=utf-8
#forms.py
from django import forms
class UsersForm(forms.Form):
        name = forms.CharField(max_length=30)
        sex = forms.CharField(max_length=6)
        age = forms.IntegerField()
        email = forms.EmailField(required=False,label='Your e-mail address')
        error_css_class = 'error'#当提示错误的时候,使用的是error类
        required_css_class = 'required'#当提示必须的时候,使用required类
        def clean_sex(self):
            sex = self.cleaned_data['sex']
            if sex not in ['male','female']:
                raise forms.ValidationError("sex item error")
            return sex
>>> from users.forms import UsersForm
>>> f = UsersForm()
>>> print f
<tr class="required"><th><label class="required" for="id_name">Name:</label></th><td><input id="id_name" maxlength="30" name="name" type="text" /></td></tr>
<tr class="required"><th><label class="required" for="id_sex">Sex:</label></th><td><input id="id_sex" maxlength="6" name="sex" type="text" /></td></tr>
<tr class="required"><th><label class="required" for="id_age">Age:</label></th><td><input id="id_age" name="age" type="number" /></td></tr>
<tr><th><label for="id_email">Your e-mail address:</label></th><td><input id="id_email" name="email" type="email" /></td></tr>
>>> 
  • 定制Form设计
    虽然,自动生成HTML是很方便的,但是在某些时候,你会想覆盖默认的显示。 {{form.as_table}}和其它的方法在开发的时候是一个快捷的方式,form的显示方式也可以在form中被方便地重写。
    每一个字段部件(<input type=”text”>, <select>, <textarea>, 或者类似)都可以通过访问{{form.字段名}}进行单独的渲染。
<html>
<head>
    <title>Show user</title>
</head>
<body>
    <h1>Show user/h1>
    {% if form.errors %}
        <p style="color: red;">
            Please correct the error{{ form.errors|pluralize }} below.
        </p>
    {% endif %}
    <form action="" method="post">
        <div class="field">
            {{ form.name.errors }}
            <label for="id_name">name:</label>
            {{ form.name }}
        </div>
        <div class="field">
            {{ form.email.errors }}
            <label for="id_email">Your e-mail address:</label>
            {{ form.email }}
        </div>
        <div class="field">
            {{ form.sex.errors }}
            <label for="id_sex">sex:</label>
            {{ form.sex }}
        </div>
        <div class="field">
            {{ form.age.errors }}
            <label for="id_age">age:</label>
            {{ form.age }}
        </div>
        <input type="submit" value="Submit">
    </form>
</body>
</html>

这样,我们就可以针对它们使用CSS。

参考文献

http://docs.30c.org/djangobook2/chapter07/
http://www.cnblogs.com/BeginMan/archive/2013/09/06/3306081.html

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!