一個視圖函數,簡稱視圖,是一個簡單的Python 函數,它接受Web請求而且返回Web響應。響應能夠是一張網頁的HTML內容,一個重定向,一個404錯誤,一個XML文檔,或者一張圖片. . . 是任何東西均可以。不管視圖自己包含什麼邏輯,都要返回響應。代碼寫在哪裏也無所謂,只要它在你的Python目錄下面。除此以外沒有更多的要求了。爲了將代碼放在某處,約定是將視圖放置在項目或應用程序目錄中的名爲views.py的文件中。html
django將請求報文中的請求行、首部信息、內容主體封裝成 HttpRequest 類中的屬性。python
""" 1、屬性 1. HttpRequest.scheme 字符串類型,表示請求的協議種類,'http'或'https'。 2. HttpRequest.body 一個字符串,表明請求報文的主體。在處理非 HTTP 形式的報文時很是有用,例如:二進制圖像、XML等。若是要處理常規的表單數據,應該使用HttpRequest.POST。 還可使用相似讀寫文件的方式從HttpRequest中讀取數據,參見HttpRequest.read()。 3. HttpRequest.path 字符串類型,表示當前請求頁面的完整路徑,可是不包括協議名和域名。例如:"/music/bands/the_beatles/"。這個屬性,常被用於咱們進行某項操做時,若是不經過,返回用戶先前瀏覽的頁面。很是有用! 4. HttpRequest.path_info 在某些Web服務器配置下,主機名後的URL部分被分紅腳本前綴部分和路徑信息部分。path_info 屬性將始終包含路徑信息部分,不論使用的Web服務器是什麼。使用它代替path可讓代碼在測試和開發環境中更容易地切換。 例如,若是應用的WSGIScriptAlias設置爲/minfo,那麼HttpRequest.path等於/music/bands/the_beatles/ ,而HttpRequest.path_info爲/minfo/music/bands/the_beatles/。 5. HttpRequest.method 字符串類型,表示請求使用的HTTP方法。默認爲大寫。 像這樣: if request.method == 'GET': do_something() elif request.method == 'POST': do_something_else() 經過這個屬性來判斷請求的方法,而後根據請求的方法不一樣,在視圖中執行不一樣的代碼。 6. HttpRequest.encoding 一個字符串,表示提交的數據的編碼方式(若是爲 None 則表示使用 DEFAULT_CHARSET 的設置,默認爲 'utf-8')。 這個屬性是可寫的,你能夠修改它來修改訪問表單數據使用的編碼。 接下來對屬性的任何訪問(例如從 GET 或 POST 中讀取數據)將使用新的 encoding 值。 若是你知道表單數據的編碼不是 DEFAULT_CHARSET ,則使用它。 7. HttpRequest.content_type Django1.10中新增。表示從CONTENT_TYPE頭解析的請求的MIME類型。 8. HttpRequest.content_params Django 1.10中新增。包含在CONTENT_TYPE標題中的鍵/值參數字典。 9 HttpRequest.GET 一個相似於字典的對象,包含GET請求中的全部參數。 詳情參考QueryDict文檔。 注意:鍵值對的值是多個的時候,好比checkbox類型的input標籤,select標籤,須要用: request.POST.getlist("hobby") 10. HttpRequest.POST 一個包含全部POST請求的參數,以及包含表單數據的字典。 詳情請參考QueryDict文檔。 若是須要訪問請求中的原始或非表單數據,可使用HttpRequest.body屬性。 注意:請使用if request.method == "POST"來判斷一個請求是否POST類型,而不要使用if request.POST。 POST中不包含上傳文件的數據。文件信息將包含在 FILES 屬性中。 11. HttpRequest.COOKIES 包含全部Cookie信息的字典。 鍵和值都爲字符串。能夠相似字典類型的方式,在cookie中讀寫數據,可是注意cookie是不安全的,所以,不要寫敏感重要的信息。 12. HttpRequest.FILES 一個相似於字典的對象,包含全部的上傳文件信息。 FILES 中的每一個鍵爲<input type="file" name="" /> 中的name,值則爲對應的數據。 注意,FILES 只有在請求的方法爲POST 且提交的<form> 帶有enctype="multipart/form-data" 的狀況下才會 包含數據。不然,FILES 將爲一個空的相似於字典的對象。 13. HttpRequest.META 包含全部HTTP頭部信息的字典。 可用的頭部信息取決於客戶端和服務器,下面是一些示例: CONTENT_LENGTH —— 請求正文的長度(以字符串計)。 CONTENT_TYPE —— 請求正文的MIME類型。 HTTP_ACCEPT —— 可接收的響應Content-Type。 HTTP_ACCEPT_ENCODING —— 可接收的響應編碼類型。 HTTP_ACCEPT_LANGUAGE —— 可接收的響應語言種類。 HTTP_HOST —— 客服端發送的Host頭部。 HTTP_REFERER —— Referring頁面。 HTTP_USER_AGENT —— 客戶端的user-agent字符串。 QUERY_STRING —— 查詢字符串。 REMOTE_ADDR —— 客戶端的IP地址。想要獲取客戶端的ip信息,就在這裏! REMOTE_HOST —— 客戶端的主機名。 REMOTE_USER —— 服務器認證後的用戶,若是可用。 REQUEST_METHOD —— 表示請求方法的字符串,例如"GET" 或"POST"。 SERVER_NAME —— 服務器的主機名。 SERVER_PORT —— 服務器的端口(字符串)。 以上只是比較重要和經常使用的,還有不少未列出。 從上面能夠看到,除CONTENT_LENGTH和CONTENT_TYPE以外,請求中的任何HTTP頭部鍵轉換爲META鍵時,都會將全部字母大寫並將鏈接符替換爲下劃線最後加上HTTP_前綴。因此,一個叫作X-Bender的頭部將轉換成META中的HTTP_X_BENDER鍵。 13. HttpRequest.resolver_match 表明一個已解析的URL的ResolverMatch實例。 2、可自定義的屬性 Django不會自動設置下面這些屬性,而是由你本身在應用程序中設置並使用它們。 1. HttpRequest.current_app 表示當前app的名字。url模板標籤將使用其值做爲reverse()方法的current_app參數。 2. HttpRequest.urlconf 設置當前請求的根URLconf,用於指定不一樣的url路由進入口,這將覆蓋settings中的ROOT_URLCONF設置。 將它的值修改成None,能夠恢復使用ROOT_URLCONF設置。 3、由中間件設置的屬性 Django的contrib應用中包含的一些中間件會在請求上設置屬性。 1. HttpRequest.session 一個既可讀又可寫的相似於字典的對象,表示當前的會話。只有當Django 啓用會話的支持時纔可用。 SessionMiddleware中間件:一個可讀寫的,相似字典的對象,表示當前會話。咱們要保存用戶狀態,回話過程等等,靠的就是這個中間件和這個屬性。 2. HttpRequest.site CurrentSiteMiddleware中間件:get_current_site()方法返回的Site或RequestSite的實例,表明當前站點是哪一個。 Django是支持多站點的,若是你同時上線了幾個站點,就須要爲每一個站點設置一個站點id。 3. HttpRequest.user(用戶認證組件下使用) AuthenticationMiddleware中間件:表示當前登陸的用戶的AUTH_USER_MODEL的實例,這個模型是Django內置的Auth模塊下的User模型。若是用戶當前未登陸,則user將被設置爲AnonymousUser的實例。 可使用is_authenticated方法判斷當前用戶是否合法用戶,以下所示: 一個 AUTH_USER_MODEL 類型的對象,表示當前登陸的用戶。 若是用戶當前沒有登陸,user 將設置爲 django.contrib.auth.models.AnonymousUser 的一個實例。你能夠經過 is_authenticated() 區分它們。 例如: if request.user.is_authenticated(): # Do something for logged-in users. else: # Do something for anonymous users. user 只有當Django 啓用 AuthenticationMiddleware 中間件時纔可用。 ------------------------------------------------------------------------------------- 匿名用戶 class models.AnonymousUser django.contrib.auth.models.AnonymousUser 類實現了django.contrib.auth.models.User 接口,但具備下面幾個不一樣點: id 永遠爲None。 username 永遠爲空字符串。 get_username() 永遠返回空字符串。 is_staff 和 is_superuser 永遠爲False。 is_active 永遠爲 False。 groups 和 user_permissions 永遠爲空。 is_anonymous() 返回True 而不是False。 is_authenticated() 返回False 而不是True。 set_password()、check_password()、save() 和delete() 引起 NotImplementedError。 New in Django 1.8: 新增 AnonymousUser.get_username() 以更好地模擬 django.contrib.auth.models.User。 """
""" 1.HttpRequest.get_full_path() 返回 path,若是能夠將加上查詢字符串。 例如:"/music/bands/the_beatles/?print=true" 2.HttpRequest.is_ajax() 若是請求是經過XMLHttpRequest 發起的,則返回True,方法是檢查 HTTP_X_REQUESTED_WITH 相應的首部是不是字符串'XMLHttpRequest'。 大部分現代的 JavaScript 庫都會發送這個頭部。若是你編寫本身的 XMLHttpRequest 調用(在瀏覽器端),你必須手工設置這個值來讓 is_ajax() 能夠工做。 若是一個響應須要根據請求是不是經過AJAX 發起的,而且你正在使用某種形式的緩存例如Django 的 cache middleware, 你應該使用 vary_on_headers('HTTP_X_REQUESTED_WITH') 裝飾你的視圖以讓響應可以正確地緩存。 """ """ 1. HttpRequest.get_host()[source] 根據HTTP_X_FORWARDED_HOST和HTTP_HOST頭部信息獲取請求的原始主機。 若是這兩個頭部沒有提供相應的值,則使用SERVER_NAME和SERVER_PORT。 例如:"127.0.0.1:8000" 注:當主機位於多個代理的後面,get_host()方法將會失敗。解決辦法之一是使用中間件重寫代理的頭部,以下面的例子: from django.utils.deprecation import MiddlewareMixin class MultipleProxyMiddleware(MiddlewareMixin): FORWARDED_FOR_FIELDS = [ 'HTTP_X_FORWARDED_FOR', 'HTTP_X_FORWARDED_HOST', 'HTTP_X_FORWARDED_SERVER', ] def process_request(self, request): Rewrites the proxy headers so that only the most recent proxy is used. for field in self.FORWARDED_FOR_FIELDS: if field in request.META: if ',' in request.META[field]: parts = request.META[field].split(',') request.META[field] = parts[-1].strip() 2. HttpRequest.get_port()[source] 使用META中HTTP_X_FORWARDED_PORT和SERVER_PORT的信息返回請求的始發端口。 3. HttpRequest.get_full_path()[source] 返回包含完整參數列表的path。例如:/music/bands/the_beatles/?print=true 4. HttpRequest.build_absolute_uri(location)[source] 返回location的絕對URI形式。 若是location沒有提供,則使用request.get_full_path()的值。 例如:"https://example.com/music/bands/the_beatles/?print=true" 注:不鼓勵在同一站點混合部署HTTP和HTTPS,若是須要將用戶重定向到HTTPS,最好使用Web服務器將全部HTTP流量重定向到HTTPS。 5. HttpRequest.get_signed_cookie(key, default=RAISE_ERROR, salt='', max_age=None)[source] 從已簽名的Cookie中獲取值,若是簽名不合法則返回django.core.signing.BadSignature。 可選參數salt用來爲密碼加鹽,提升安全係數。 max_age參數用於檢查Cookie對應的時間戳是否超時。 6. HttpRequest.is_secure()[source] 若是使用的是Https,則返回True,表示鏈接是安全的。 7. HttpRequest.is_ajax()[source] 若是請求是經過XMLHttpRequest生成的,則返回True。 這個方法的做用就是判斷,當前請求是否經過ajax機制發送過來的。 8. HttpRequest.read(size=None)[source] 9. HttpRequest.readline()[source] 10. HttpRequest.readlines()[source] 11. HttpRequest.xreadlines()[source] 12. HttpRequest.iter() 上面的幾個方法都是從HttpRequest實例讀取文件數據的方法。 能夠將HttpRequest實例直接傳遞到XML解析器,例如ElementTree: import xml.etree.ElementTree as ET for element in ET.iterparse(request): process(element) """
響應對象主要有三種形式:web
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
|
"""
render(request, template_name[, context])
結合一個給定的模板和一個給定的上下文字典,並返回一個渲染後的 HttpResponse 對象。
參數:
request: 用於生成響應的請求對象。
template_name:要使用的模板的完整名稱,可選的參數
context:添加到模板上下文的一個字典。默認是一個空字典。若是字典中的某個值是可調用的,視圖將在渲染模板以前調用它。
render方法就是將一個模板頁面中的模板語法進行渲染,最終渲染成一個html頁面做爲響應體。
"""
return
render(request,
"index.html"
,{
"timer"
:ctime})
# index.html 模板文件
# return render(request, "index.html", locals()) #
# HttpResponse
return
HttpResponse(reverse(
"app01:index"
))
return
HttpResponse(
"<h1>OK</h1>"
)
#redirect
return
redirect(
"/index/"
)
return
redirect(
'http://baidu.com/'
)
|
""" 1、使用方法 1. 傳遞一個字符串 return HttpResponse("<h1>OK</h1>") 2. 傳遞可迭代對象 HttpResponse會當即處理這個迭代器,並把它的內容存成字符串,最後廢棄這個迭代器。好比文件在讀取後,會馬上調用close()方法,關閉文件。 3. 設置頭部字段 能夠把HttpResponse對象看成一個字典同樣,在其中增長和刪除頭部字段。 >>> response = HttpResponse() >>> response['Age'] = 120 >>> del response['Age'] 注意!與字典不一樣的是,若是要刪除的頭部字段若是不存在,del不會拋出KeyError異常。 HTTP的頭部字段中不能包含換行。因此若是咱們提供的頭部字段值包含換行符(CR或者LF),將會拋出BadHeaderError異常。 4. 告訴瀏覽器將響應視爲文件附件 讓瀏覽器以文件附件的形式處理響應, 須要聲明content_type類型和設置Content-Disposition頭信息。 例如,給瀏覽器返回一個微軟電子表格: >>> response = HttpResponse(my_data, content_type='application/vnd.ms-excel') >>> response['Content-Disposition'] = 'attachment; filename="foo.xls"' 2、屬性 1. HttpResponse.content 響應的內容。bytes類型。 2. HttpResponse.charset 編碼的字符集。 若是沒指定,將會從content_type中解析出來。 3. HttpResponse.status_code 響應的狀態碼,好比200。 4. HttpResponse.reason_phrase 響應的HTTP緣由短語。 使用標準緣由短語。 除非明確設置,不然reason_phrase由status_code的值決定。 5. HttpResponse.streaming 這個屬性的值老是False。因爲這個屬性的存在,使得中間件可以區別對待流式響應和常規響應。 6. HttpResponse.closed 若是響應已關閉,那麼這個屬性的值爲True。 3、 方法 1. HttpResponse.init(content='', content_type=None, status=200, reason=None, charset=None)[source] 響應的實例化方法。使用content參數和content-type實例化一個HttpResponse對象。 content應該是一個迭代器或者字符串。若是是迭代器,這個迭代期返回的應是一串字符串,而且這些字符串鏈接起來造成response的內容。 若是不是迭代器或者字符串,那麼在其被接收的時候將轉換成字符串。 content_type是可選地,用於填充HTTP的Content-Type頭部。若是未指定,默認狀況下由DEFAULT_CONTENT_TYPE和DEFAULT_CHARSET設置組成:text/html; charset=utf-8。 status是響應的狀態碼。reason是HTTP響應短語。charset是編碼方式。 2. HttpResponse.has_header(header) 檢查頭部中是否有給定的名稱(不區分大小寫),返回True或 False。 3. HttpResponse.setdefault(header, value) 設置一個頭部,除非該頭部已經設置過了。 4. HttpResponse.set_cookie(key, value='', max_age=None, expires=None, path='/', domain=None, secure=None, httponly=False) 設置一個Cookie。 參數與Python標準庫中的Morsel.Cookie對象相同。 max_age: 生存週期,以秒爲單位。 expires:到期時間。 domain: 用於設置跨域的Cookie。例如domain=".lawrence.com"將設置一個www.lawrence.com、blogs.lawrence.com和calendars.lawrence.com均可讀的Cookie。 不然,Cookie將只能被設置它的域讀取。 若是你想阻止客服端的JavaScript訪問Cookie,能夠設置httponly=True。 5. HttpResponse.set_signed_cookie(key, value, salt='', max_age=None, expires=None, path='/', domain=None, secure=None, httponly=True) 與set_cookie()相似,可是在設置以前將對cookie進行加密簽名。一般與HttpRequest.get_signed_cookie()一塊兒使用。 6. HttpResponse.delete_cookie(key, path='/', domain=None) 刪除Cookie中指定的key。 因爲Cookie的工做方式,path和domain應該與set_cookie()中使用的值相同,不然Cookie不會刪掉。 7. HttpResponse.write(content)[source] 將HttpResponse實例看做相似文件的對象,往裏面添加內容。 8. HttpResponse.flush() 清空HttpResponse實例的內容。 9. HttpResponse.tell()[source] 將HttpResponse實例看做相似文件的對象,移動位置指針。 10. HttpResponse.getvalue()[source] 返回HttpResponse.content的值。 此方法將HttpResponse實例看做是一個相似流的對象。 11. HttpResponse.readable() Django1.10中的新功能,值始終爲False。 12. HttpResponse.seekable() Django1.10中的新功能,值始終爲False。 13. HttpResponse.writable()[source] Django1.10中的新功能,值始終爲True。 14. HttpResponse.writelines(lines)[source] 將一個包含行的列表寫入響應對象中。 不添加分行符。 4、HttpResponse的子類 Django包含了一系列的HttpResponse衍生類(子類),用來處理不一樣類型的HTTP響應。與HttpResponse相同, 這些衍生類存在於django.http之中。 class HttpResponseRedirect[source]:重定向,返回302狀態碼。已經被redirect()替代。 class HttpResponsePermanentRedirect[source]:永久重定向,返回301狀態碼。 class HttpResponseNotModified[source]:未修改頁面,返回304狀態碼。 class HttpResponseBadRequest[source]:錯誤的請求,返回400狀態碼。 class HttpResponseNotFound[source]:頁面不存在,返回404狀態碼。 class HttpResponseForbidden[source]:禁止訪問,返回403狀態碼。 class HttpResponseNotAllowed[source]:禁止訪問,返回405狀態碼。 class HttpResponseGone[source]:過時,返回405狀態碼。 class HttpResponseServerError[source]:服務器錯誤,返回500狀態碼。 5、JsonResponse類 class JsonResponse(data,encoder = DjangoJSONEncoder,safe = True,json_dumps_params = None ,** kwargs)[source] JsonResponse是HttpResponse的一個子類,是Django提供的用於建立JSON編碼類型響應的快捷類。 它從父類繼承大部分行爲,並具備如下不一樣點: 它的默認Content-Type頭部設置爲application/json。 它的第一個參數data,一般應該爲一個字典數據類型。 若是safe參數設置爲False,則能夠是任何可JSON 序列化的對象。 encoder默認爲django.core.serializers.json.DjangoJSONEncoder,用於序列化數據。 布爾類型參數safe默認爲True。 若是設置爲False,能夠傳遞任何對象進行序列化(不然,只容許dict 實例)。 典型的用法以下: >>> from django.http import JsonResponse >>> response = JsonResponse({'foo': 'bar'}) >>> response.content b'{"foo": "bar"}' 若要序列化非dict對象,必須設置safe參數爲False: >>> response = JsonResponse([1, 2, 3], safe=False) 若是不傳遞safe=False,將拋出一個TypeError。 若是你須要使用不一樣的JSON 編碼器類,能夠傳遞encoder參數給構造函數: >>> response = JsonResponse(data, encoder=MyJSONEncoder) 6、StreamingHttpResponse類 StreamingHttpResponse類被用來從Django響應一個流式對象到瀏覽器。若是生成的響應太長或者是佔用的內存較大,這麼作可能更有效率。 例如,它對於生成大型的CSV文件很是有用。 StreamingHttpResponse不是HttpResponse的衍生類(子類),由於它實現了徹底不一樣的應用程序接口。可是,除了幾個明顯不一樣的地方,二者幾乎徹底相同。 7、FileResponse 文件類型響應。一般用於給瀏覽器返回一個文件附件。 FileResponse是StreamingHttpResponse的衍生類,爲二進制文件專門作了優化。 FileResponse須要經過二進制模式打開文件,以下: >>> from django.http import FileResponse >>> response = FileResponse(open('myfile.png', 'rb')) """
當Django找不到與請求匹配的URL時,或者當拋出一個異常時,將調用一個錯誤處理視圖。錯誤視圖包括400、40三、404和500,分別表示請求錯誤、拒絕服務、頁面不存在和服務器錯誤。它們分別位於ajax
這些值能夠在根URLconf中設置。在其它app中的二級URLconf中設置這些變量無效。django
Django有內置的HTML模版,用於返回錯誤頁面給用戶,可是這些403,404頁面實在醜陋,一般咱們都自定義錯誤頁面。json
首先,在根URLconf中額外增長下面的條目:跨域
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
from
django.conf.urls
import
url
from
django.conf.urls
import
include
from
django.contrib
import
admin
from
.
import
views
urlpatterns
=
[
url(r
'^admin/'
, admin.site.urls),
url(r
'^backend/'
,include(
'backend.urls'
)),
url(r
'^'
, include(
'web.urls'
)),
]
# 增長的條目
handler400
=
views.bad_request
handler403
=
views.permission_denied
handler404
=
views.page_not_found
handler500
=
views.page_error
|
而後在,views.py文件中增長四個處理視圖:瀏覽器
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
|
from
django.shortcuts
import
render
def
page_not_found(request):
return
render(request,
'404.html'
)
def
page_error(request):
return
render(request,
'500.html'
)
def
permission_denied(request):
return
render(request,
'403.html'
)
def
bad_request(request):
return
render(request,
'400.html'
)
|