W3Cschool
恭喜您成為首批注冊用戶
獲得88經(jīng)驗(yàn)值獎勵
假設(shè)您希望在您的網(wǎng)站上創(chuàng)建一張簡易的表單,用來獲取用戶的名字。您需要在模板中使用類似代碼:
<form action="/your-name/" method="post">
<label for="your_name">Your name: </label>
<input id="your_name" type="text" name="your_name" value="{{ current_name }}">
<input type="submit" value="OK">
</form>
這告訴瀏覽器將表單數(shù)據(jù)返回給URL ?/your-name/
? ,并使用 ?POST
?方法。它將顯示一個標(biāo)簽為 "Your name:" 的文本字段,以及一個 "OK" 按鈕。如果模板上下文包含一個 ?current_name
?變量,它會被預(yù)填充到 ?your_name
?字段。
您需要一個視圖來渲染這個包含HTML表單的模板,并能適當(dāng)提供 ?current_name
?字段。
提交表單時,發(fā)送給服務(wù)器的 POST 請求將包含表單數(shù)據(jù)。
現(xiàn)在,您還需要一個與該 ?/your-name/
? URL相對應(yīng)的視圖,該視圖將在請求中找到相應(yīng)的鍵/值對,然后對其進(jìn)行處理。
這是一張非常簡單的表單。實(shí)際應(yīng)用中,一張表單可能包含數(shù)十上百的字段,其中許多可能需要預(yù)填充,并且我們可能希望用戶在結(jié)束操作前需要多次來回編輯-提交。
我們可能需要在瀏覽器中進(jìn)行一些驗(yàn)證,甚至在表單提交之前;我們可能希望使用更復(fù)雜的字段 ,以允許用戶做類似日期選擇等操作。
此刻,我們很容易通過使用Django來完成以上大部分工作。
我們已經(jīng)很清楚想要的HTML表單看起來會是什么樣子。首先,在Django中這樣做:
from django import forms
class NameForm(forms.Form):
your_name = forms.CharField(label='Your name', max_length=100)
它定義了一個只包含一個字段( ?your_name
?)的 ?Form
?類。我們已經(jīng)為這個字段提供了友好的標(biāo)簽,當(dāng)它渲染后會顯示在 ?<label>
? 中(在這種情況下,如果我們省略之前指定的 label ,它還是會自動生成一個一樣的標(biāo)簽)。
字段的最大長度由 ?max_length
?來定義。它做了兩件事情。首先它在HTML的 ?<input>
? 上增加了 ?maxlength="100"
? (這樣瀏覽器會在第一時間阻止用戶輸入超過這個數(shù)量的字符串)。其次它還會在Django收到瀏覽器傳過來的表單時,對數(shù)據(jù)長度進(jìn)行驗(yàn)證(也就是服務(wù)器端驗(yàn)證)。
Form 實(shí)例有一個 ?is_valid()
? 方法,該方法對其所有字段運(yùn)行驗(yàn)證例程。 調(diào)用此方法時,如果所有字段都包含有效數(shù)據(jù),它將:
True
?cleaned_data
?中這樣整個表單在第一次渲染時,會顯示如下:
<label for="your_name">Your name: </label>
<input id="your_name" type="text" name="your_name" maxlength="100" required>
發(fā)回Django網(wǎng)站的表單數(shù)據(jù)由視圖來處理,一般和發(fā)布這個表單用的是同一個視圖。這允許我們重用一些相同的邏輯。
為了處理表單,我們需要將它實(shí)例化到我們希望發(fā)布的URL的對應(yīng)的視圖中:
from django.http import HttpResponseRedirect
from django.shortcuts import render
from .forms import NameForm
def get_name(request):
# if this is a POST request we need to process the form data
if request.method == 'POST':
# create a form instance and populate it with data from the request:
form = NameForm(request.POST)
# check whether it's valid:
if form.is_valid():
# process the data in form.cleaned_data as required
# ...
# redirect to a new URL:
return HttpResponseRedirect('/thanks/')
# if a GET (or any other method) we'll create a blank form
else:
form = NameForm()
return render(request, 'name.html', {'form': form})
如果我們訪問這個視圖用的是 ?GET
?請求,它會創(chuàng)建一個空的表單實(shí)例并將其放置在模板上下文中進(jìn)行渲染。這是我們在首次訪問這個URL時能預(yù)料到會發(fā)生的情況。
如果表單提交用的是 ?POST
?請求,那么該視圖將再次創(chuàng)建一個表單實(shí)例并使用請求中的數(shù)據(jù)填充它: ?form = NameForm(request.POST)
?,這叫“綁定數(shù)據(jù)到表單” (現(xiàn)在它是一張 綁定的 表單)。
我們調(diào)用表單的 ?is_valid()
? 方法;如果不為 ?True
?,我們帶著表單返回到模板。這次表單不再為空( 未綁定 ),所以HTML表單將用之前提交的數(shù)據(jù)進(jìn)行填充,放到可以根據(jù)需要進(jìn)行編輯和修正的位置。
如果 ?is_valid()
? 為 ?True
?,我們就能在其 ?cleaned_data
?屬性中找到所有通過驗(yàn)證的表單數(shù)據(jù)。我們可以在發(fā)送一個HTTP重定向告訴瀏覽器下一步去向之前用這些數(shù)據(jù)更新數(shù)據(jù)庫或者做其他處理。
我們沒有必要在模板 ?name.html
? 中做過多的操作:
<form action="/your-name/" method="post">
{% csrf_token %}
{{ form }}
<input type="submit" value="Submit">
</form>
所有的表單字段及其屬性都將通過Django模板語言從 ?{{ form }}
?中被解包成HTML標(biāo)記。
Django自帶一個簡單易用的 跨站請求偽造防護(hù) 。當(dāng)通過 POST 方法提交一張啟用了CSRF防護(hù)的表單時,您必須使用上例中這樣的模板標(biāo)簽 ?csrf_token
?。但是,由于CSRF防護(hù)在模板中沒有與表單直接綁定,因此這個標(biāo)簽在本頁文檔之后的示例中都將被忽略。
如果您的表單包含 ?URLField
?, ?EmailField
?或者其他整數(shù)字段類型,Django將使用 url , email 和 number HTML5輸入類型。默認(rèn)情況下,瀏覽器可能會在這些字段上應(yīng)用他們自己的驗(yàn)證,這也許比Django的驗(yàn)證更加嚴(yán)格。如果您想禁用這個行為,請在 form 標(biāo)簽上設(shè)置 ?novalidate
?屬性,或者在字段上指定一個不同的控件,比如 ?TextInput
?
現(xiàn)在我們有了一個可以工作的web表單,它通過一張Django ?Form
?描述,由一個視圖來處理并渲染成一個HTML ?<form>
? 。
Copyright©2021 w3cschool編程獅|閩ICP備15016281號-3|閩公網(wǎng)安備35020302033924號
違法和不良信息舉報電話:173-0602-2364|舉報郵箱:jubao@eeedong.com
掃描二維碼
下載編程獅App
編程獅公眾號
聯(lián)系方式:
更多建議: