程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式師世界 >> 編程語言 >  >> 更多編程語言 >> Python

【武sir】django rest framework源碼和實戰_day01(上)

編輯:Python

 (0)摘要

# 課程鏈接

4天搞定django rest framework源碼和實戰_哔哩哔哩_bilibili

# 課程內容

(1)內容概要_略

(2)內容回顧_略

(3)django 視圖之 CBV 基本使用

(4)django 視圖之 CBV 源碼流程

(5)django 視圖之面試題和 csrf 補充

(6)django 視圖之 CBV 和解決 csrf 認證

(7)以上內容梳理_略

【知識點補充---自己加的】


# 豈曰無衣,與子同袍

(2)內容回顧_略

# (1)直接上圖


# (2)Django 的 FBV 和 CBV

                1)FBV 就是基於函數的視圖, 就跟我們平時使用的一樣。

                2)CBV 是基於類的視圖。就是要繼承 django.views 中的 View 。見下圖所示的代碼。當執行了這一個類的時候,前端傳來是什麼請求,類就會自動執行相應的方法。比如 post 請求,那麼類就會執行 post 的方法。

                此時路由函數要這麼寫,就是要加 .as_view() 來作為路由函數,這裡是固定的要求,不為什麼。 

                那麼上面就是一個 CBV 的模式。


# (3)postman 偽造請求

                1)我們不可能為每一種請求再去設計相應的表單提交什麼的,這沒意義。我們可以使用 postman 這種工具來偽造各種請求,來查看後端返回的數據。

                

                2)postman 的下載安裝。下載鏈接:Download Postman | Get Started for Free

// 下載完成後,我們直接打開後就會自動安裝了,並且在桌面生成快捷方式。這個時候打開該快捷方式,即如下圖所示。其實 postman 有網頁端,但是需要桌面代理才能測試本地的 url 。 

                3)postman 簡單使用。如下圖所示,我們點了加號之後的頁面,然後我們也具體的使用了下,測試了 post 請求。這裡的報錯是因為我們沒有關閉 django 中的 csrf 認證。這裡可以直接去 settings.py 文件中的中間件處注釋掉該認證即可。


# (4)列表生成式,直接給我寫的代碼和注釋吧


# (5)面向對象

                1)封裝。體現在兩個方面,一個方面是對同一類方法封裝到類中。如下圖所示,就是將各自類的對應自己方法,然後進行封裝。 

               

                另外一個是將數據封裝到對象中,就是我們將數據傳入到類裡面,然後裡面的 self.a1 = 傳參 a1,大致就是這個意思,供類的調用,也就是我們實例化這個類後,我們不僅能使用類的方法,還有裡面的數據。

                2)簡單聊聊裝飾器 @property,這個裝飾器的作用會在別的數據分析的課裡面細講,我們只需要知道,在定義函數的前面引用。之後我們在調用該函數的時候,就可以不加括號了,就跟調用屬性一樣。見下面的代碼塊,算是一種入門級別的理解吧。

# -*- coding=utf-8 -*-
# github: night_walkiner
# csdn: 潘迪仔
class Foo:
def __init__(self):
self.price = 100
# (1) 裝飾器,這裡必須寫在最前面,函數名就是後續調用時候用的,
# 而且 @property 裝飾後的函數,必須是返回某個值,然後調用是屬性調用,就是對方法不用加括號
# 這裡必須提一句,如果我們之後要賦值,比如下面的代碼:
"""
類 Foo 下的
@property
def price(self,value):
pass
之後調用的時候,如果我們 Foo.price 會提示少一個參數,
而如果我們這樣 Foo.price(100) ,依然會報錯,
因此我們要使用裝飾器要求的設置,即下面的方式來設置數值什麼的
"""
@property
def price(self):
return print("裝飾器")
# 如果今後我們要對 price 進行賦值的話,必須裝飾 price.setter ,
# 注意觀察啊!!!
@price.setter
def price(self, value):
self.price = value
# 這個是一樣的,也是要用(1) 中定義的 price 來 .deleter 作為裝飾器
@price.deleter
def price(self):
del self.price

                那麼來上一個實例看看,就是武 sir 寫的代碼,我就不復現了。這裡是也是封裝實例的擴展,很簡單。如果遇到問題去復現一下,或者研讀下吧,不贅述了。


(3)django 視圖之 CBV 基本使用

# (1)內容詳細

                1)關於 CBV 開發的結構。事實上 HTTP 請求本質上是發了一堆字符串,通過 /r 進行分隔的。但是我們是怎麼處理請求的呢? Django 源碼中是使用反射來做的,也就是 getattr() 方法來做。如果不使用反射方法,我們就要使用 request.method 去一個個做判斷執行。(基本所有支持 CBV 結構的框架都是使用反射去實現的)

                2)對於 CBV 而言,我們使用了這種模式的時候,實際上就是在路由地址,執行了 as_view() 的方法,然後我們可以看 as_view() 的源碼,可以看到不論是執行什麼請求,都要執行 self.dispatch() 

                 

                3)self.dispatch 的源碼如下,首先將獲取的 request.method 的請求變小寫,比如原來的是 GET 變成 get,然後判斷這個請求是不是在  self.http_method_names 裡面,這個self.http_method_names 裡面存著的是各自請求類型,如 post,put 等等。 getattr(x, "y") 相當於 x.y 的意思,類似屬性調用。

                4)CBV 的具體流程

                5)父類和子類的方法的執行順序。見下圖所示的代碼:

                如下圖所示,比如當前是 post 請求,然後我們執行了 dispatch 方法。

                第一: 那麼系統就會從子類中找到 dispatch ,子類又會去父類裡面找父類的 dispatch,但是 self 是代指子類,經過反射後找到的是 post 請求,

                第二: 然後再從子類中調用 post 方法,將結果再返回給父類的 dispatch, 父類的 dispatch 再傳回給子類的 dispatch ,然後再返回給用戶。


(4)django 視圖之 CBV 源碼流程(最好再多想想,這一塊老師講的不是很清晰)

# (1)CBV 源碼流程的補充。相信這一塊會隨著深入學習而更扎實,且有更好的理解。


# (2) 繼承


(5)django 視圖之面試題和 csrf 補充

# (1)Django 中間件

                1)Django 中間件最多只能寫 5 個方法,就是下圖列舉的。以前說的 process_request() 和 process_response() 兩種方法是最常用的而已。

                其中 process_exception() 方法是只有異常的時候才會執行,沒有異常就不會執行。對於 process_render_template() 方法,如果視圖函數返回的是 render() 就會執行這個中間件,否則執行 HttpResponse() 的話是永遠不會執行。

                

               

                2)中間件的執行流程 _(Django 1.10 以上的版本),見下圖所示,我們簡述一下中間件的執行流程,當請求進來的時候:

                第一:首先是按序執行所有中間件的 process_request() 方法,然後進行路由匹配,但是不執行視圖函數;

                第二:執行完路由匹配後,再返回第一層中間件,繼續按序執行他們的 process_view() 方法,執行完後才開始執行視圖函數;

                第三:視圖函數正確執行和返回(HttpResponse)的時候,就開始執行 process_response() 方法返回給浏覽器。

                第四:如果說,在執行路由函數時候發生錯誤,那麼就會執行 process_exception() 方法返回異常;

                第五:如果說,視圖函數正確執行了,但是返回的是 render() 那麼就執行中間件的process_render_template() 方法,然後返回給浏覽器。

【第四、第五就是下圖見注釋的部分。】

                3)使用中間件能做什麼?比較常用的就是權限認證和用戶登錄認證。


# (2)csrf 認證的面試題

                1)Django 中的中間件 csrf_token 的實現。csrf 的中間件是寫在了 process_view() 方法裡面的。【見後面的(3)的 3)的講解】


# (3)免除 csrf 認證裝飾器和單獨 csrf 認證的裝飾器

                1)假設我們將全局的視圖函數都添加了 csrf 認證,也就是在中間件的地方給 csrf 打開認證了,那麼我們如果想免除某個視圖函數的 csrf 認證就可以使用免除認證的裝飾器了。那麼導入的模塊語句為:from django.views.decorators.csrf import csrf_exempt

如下圖所示,那麼我們在視圖函數 users 前引用了 @csrf_exempt 就是免除該函數的 csrf 認證了。 

                2)場景二,如果我們注釋了全局的 csrf 認證,又想對某幾個特定的視圖函數加上 csrf 認證,那麼就可以使用單獨的 csrf 裝飾器了。導入模塊的語句為:from django.views.decorators.csrf import csrf_protect  。使用方法是和免除的裝飾器一樣的。如下圖所示。

                3)有了上面的基礎,我們就知道為什麼 csrf 的認證需要寫在 process_view() 中了,這是因為在執行認證的時候,需要檢索這個視圖函數是否免除了認證(或者帶有認證),這裡面是需要邏輯判斷的。而如果寫在 process_request() 方法中,請求過程並沒有路由匹配的信息,csrf 都沒找到視圖函數,還談什麼檢查視圖函數是否帶有相應的裝飾器!緊接著,如果需要 csrf 認證,那麼再去檢查是否符合 csrf_token 的規則


(6)django 視圖之 CBV 和解決 csrf 認證

# (1)CBV 怎麼自定義 csrf 認證(自定義就是免除還是單獨設置認證)

                1)前面我們講的都是基於 FBV 的來講解 csrf 裝飾器的用法的。那麼對於 CBV 要自定義 csrf 認證的話,就不是簡單的在類中的函數上加裝飾器了。【csrf 裝飾器就是 csrf_exempt 或者 csrf_protect】

               

                2)解決方法就是使用  from django.utils.decorators import method_decorator 中的 method_decorator 裝飾器,這可以對 CBV 結構設置自定義 csrf 裝飾器用的。比如第一種方法就是如下的方法,@method_decorator(csrf_exempt) 那麼就是免除這個視圖類的 csrf 認證(對於單獨設置也是一樣的)。其實就是 @method_decorator(csrf 裝飾器),只要是按照如下的格式就行。

class StudentsView(View):
# 自定義認證---方法一, 就是放在 dispatch 方法前面。
# 這是官方規定的,沒有為什麼。
@method_decorator(csrf_exempt)
def dispatch(self, request, *args, **kwargs):
print("before")
# super() 不是簡單的繼承當前類的父類,而是執行整個繼承關系
# 也就是說,找方法的時候,先在自己裡面找,找不到采取父類找,
# 如果父類再找不到,就去第二繼承類去找
ret = super(StudentsView, self).dispatch(request, *args, **kwargs)
# print(ret)
print("after")
return ret
def get(self, request, *args, **kwargs):
print("get")
return HttpResponse("GET")
# @method_decorator(csrf_exempt) 如果是加在這裡是沒用的!!!
#(也就是對單獨方法是無效的)
# 因為官方規定了,就是要放在 dispatch 方法上面,而且 dispatch 還得放在最前面。
def post(self, request, *args, **kwargs):
return HttpResponse("POST")
def put(self, request, *args, **kwargs):
return HttpResponse("PUT")
def delete(self, request, *args, **kwargs):
return HttpResponse("DELETE")

               

                3)也可以是下面的方法,就是放在視圖類的最上面,但是編寫的時候就是@method_decorator(csrf 裝飾器,name="dispatch")。具體見下面代碼的注釋。

from django.utils.decorators import method_decorator
from django.views.decorators.csrf import csrf_exempt, csrf_protect
# 自定義認證---方法二, name裡面其實就是方法名。簡單說就是找到這個類方法,然後加上這個裝飾器
@method_decorator(csrf_exempt, name="dispatch")
class StudentsView(View):
def get(self, request, *args, **kwargs):
print("get")
return HttpResponse("GET")
def post(self, request, *args, **kwargs):
return HttpResponse("POST")
def put(self, request, *args, **kwargs):
return HttpResponse("PUT")
def delete(self, request, *args, **kwargs):
return HttpResponse("DELETE")


(7)以上內容梳理_略

# 直接上圖


【補充知識】

# (1)getattr() 反射的使用。

                還得提一點就是比如 getattr(obj, '_negotiator', None),就是返回 obj._negotiator,如果有的話。我們之前說了,如果沒這個屬性,反射就會報錯,這個時候就可以用後面 None 了,意思是說,如果沒有這個屬性,系統也不報錯,而是會返回一個 None。


# (2)類繼承的優先級



  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式師世界 All Rights Reserved