Backend-DRF-關於DRF認證機制源碼

更新於 發佈於 閱讀時間約 11 分鐘

本篇藉由追蹤DRF認證的源碼,幫助初學者能夠更佳理解其相關機制。

以下是簡單的Authentication寫法:

# setting.py 
# 全局認證設定

REST_FRAMEWORK = {
"DEFAULT_AUTHENTICATION_CLASSES": ["authentication.auth.MyAuthentication"]
}


# authentication/auth.py

class MyAuthentication(BaseAuthentication):
def authenticate(self, request):
token = request.query_params.get('token')
# 假設request有帶token就給過
if token:
return ('user', token)
raise AuthenticationFailed({"code": "401", "message": "Unauthorized"})


# app/views.py
# 提供2個view

class UserView(APIView):
authentication_classes = []
def get(self, request):
print(request.user, request.auth)
return Response({'message': 'success'})


class LoginView(APIView):
def get(self, request):
print(request.user, request.auth)
return Response({'message': 'success'})


# 路由

urlpatterns = [
path('user/', UserView.as_view()),
path('login/', LoginView.as_view()),
]

從源碼分析,以上執行as_view()方法,將返回view作為路由的callback function,並在接收request時執行dispatch,透過反射到我們自定義類中的方法 (get, post, delete, put ...)

# as_view()返回view函式,view函式執行dispatch
def as_view(cls, **initkwargs):
def view(request, *args, **kwargs):
self = cls(**initkwargs)
self.setup(request, *args, **kwargs)
if not hasattr(self, "request"):
raise AttributeError(
"%s instance has no 'request' attribute. Did you override "
"setup() and forget to call super()?" % cls.__name__
)
return self.dispatch(request, *args, **kwargs)
return view


def dispatch(self, request, *args, **kwargs):
self.args = args
self.kwargs = kwargs
request = self.initialize_request(request, *args, **kwargs)
self.request = request
self.headers = self.default_response_headers # deprecate?

try:
self.initial(request, *args, **kwargs)

if request.method.lower() in self.http_method_names:
handler = getattr(self, request.method.lower(),
self.http_method_not_allowed)
else:
handler = self.http_method_not_allowed
response = handler(request, *args, **kwargs)

從上可以觀察到DRF有針對Django的request再進行封裝:

request = self.initialize_request(request, *args, **kwargs)
self.request = request


# 增加 authenticators
def initialize_request(self, request, *args, **kwargs):
return Request(
request,
parsers=self.get_parsers(),
authenticators=self.get_authenticators(),
negotiator=self.get_content_negotiator(),
parser_context=parser_context
)

# authenticators的內容​
authentication_classes = api_settings.DEFAULT_AUTHENTICATION_CLASSES
def get_authenticators(self):
return [auth() for auth in self.authentication_classes]

APIView下的 authentication_classes 是api_settings.DEFAULT_AUTHENTICATION_CLASSES,也就是我們一開始在settings.py設定的位置。而如果像我們在自定義類UserView中有設定authentication_classes = [],依繼承規則會優先去使用。

在dispatch中會使用initial,其內最終就會用到request.user,還記得我前一篇文章嗎?

self.initial(request, *args, **kwargs)


# initail 內有 perform_authentication (其他程式碼省略)
def initial(self, request, *args, **kwargs):
self.perform_authentication(request)


# 使用到 request.user​
def perform_authentication(self, request):
request.user

至於request.user是在哪裡給值的呢?我們再觀察一下源碼,[auth() for auth in self.authentication_classes] 中會分別取authentication_classes內的類並實例化成對象:

def get_authenticators(self):
return [auth() for auth in self.authentication_classes]

在Request類的源碼,會依次嘗試每個認證器進行認證,直到有一個成功,或者所有認證器都失敗

# 一開始沒有_user,故執行self._authenticate()
@property
def user(self):
if not hasattr(self, '_user'):
with wrap_attributeerrors():
self._authenticate()

return self._user

# ​user_auth_tuple 為我們定義認證類成功的返回值 ('user', token)
def _authenticate(self):
for authenticator in self.authenticators:
try:
user_auth_tuple = authenticator.authenticate(self)
except exceptions.APIException:
self._not_authenticated()
raise

if user_auth_tuple is not None:
self._authenticator = authenticator
self.user, self.auth = user_auth_tuple
return

self._not_authenticated()

依然承接前篇文章,若認證失敗或沒設定認證器,則會進入_not_authenticated。

如果在純淨版把一些app拿掉,沒有給UNAUTHENTICATED_USER,這邊就會造成報錯了。

def _not_authenticated(self):
self._authenticator = None
if api_settings.UNAUTHENTICATED_USER:
self.user = api_settings.UNAUTHENTICATED_USER()
else:
self.user = None
if api_settings.UNAUTHENTICATED_TOKEN:
self.auth = api_settings.UNAUTHENTICATED_TOKEN()
else:
self.auth = None

以上為DRF認證機制的源碼解析,希望你們會喜歡!

留言
avatar-img
留言分享你的想法!
avatar-img
YO!全端之路 😤😤😤
0會員
2內容數
一位離開半導體業的資料科學家, 在全端掙扎的日誌
你可能也想看
Thumbnail
每年4月、5月都是最多稅要繳的月份,當然大部份的人都是有機會繳到「綜合所得稅」,只是相當相當多人還不知道,原來繳給政府的稅!可以透過一些有活動的銀行信用卡或電子支付來繳,從繳費中賺一點點小確幸!就是賺個1%~2%大家也是很開心的,因為你們把沒回饋變成有回饋,就是用卡的最高境界 所得稅線上申報
Thumbnail
每年4月、5月都是最多稅要繳的月份,當然大部份的人都是有機會繳到「綜合所得稅」,只是相當相當多人還不知道,原來繳給政府的稅!可以透過一些有活動的銀行信用卡或電子支付來繳,從繳費中賺一點點小確幸!就是賺個1%~2%大家也是很開心的,因為你們把沒回饋變成有回饋,就是用卡的最高境界 所得稅線上申報
Thumbnail
全球科技產業的焦點,AKA 全村的希望 NVIDIA,於五月底正式發布了他們在今年 2025 第一季的財報 (輝達內部財務年度為 2026 Q1,實際日曆期間為今年二到四月),交出了打敗了市場預期的成績單。然而,在銷售持續高速成長的同時,川普政府加大對於中國的晶片管制......
Thumbnail
全球科技產業的焦點,AKA 全村的希望 NVIDIA,於五月底正式發布了他們在今年 2025 第一季的財報 (輝達內部財務年度為 2026 Q1,實際日曆期間為今年二到四月),交出了打敗了市場預期的成績單。然而,在銷售持續高速成長的同時,川普政府加大對於中國的晶片管制......
Thumbnail
重點摘要: 6 月繼續維持基準利率不變,強調維持高利率主因為關稅 點陣圖表現略為鷹派,收斂 2026、2027 年降息預期 SEP 連續 2 季下修 GDP、上修通膨預測值 --- 1.繼續維持利率不變,強調需要維持高利率是因為關稅: 聯準會 (Fed) 召開 6 月利率會議
Thumbnail
重點摘要: 6 月繼續維持基準利率不變,強調維持高利率主因為關稅 點陣圖表現略為鷹派,收斂 2026、2027 年降息預期 SEP 連續 2 季下修 GDP、上修通膨預測值 --- 1.繼續維持利率不變,強調需要維持高利率是因為關稅: 聯準會 (Fed) 召開 6 月利率會議
Thumbnail
這篇文章記錄了一些網路相關名詞,包含資安、DNS、TCP/IP 等,並以淺顯易懂的方式進行解釋。適合對網路技術有興趣,但名詞理解上有困難的人閱讀。
Thumbnail
這篇文章記錄了一些網路相關名詞,包含資安、DNS、TCP/IP 等,並以淺顯易懂的方式進行解釋。適合對網路技術有興趣,但名詞理解上有困難的人閱讀。
Thumbnail
這是一篇網頁前端的基礎教學,介紹網頁前端及後端基礎觀念、環境安裝。 完整的教學會用簡單好理解的方法幫助你更快理解,避免初學者踩到更多的坑。也會教你如何善用AI輔助開發,但同時培養Debug能力,避免完全依賴工具。讓你從零開始,扎實踏上前端之路。
Thumbnail
這是一篇網頁前端的基礎教學,介紹網頁前端及後端基礎觀念、環境安裝。 完整的教學會用簡單好理解的方法幫助你更快理解,避免初學者踩到更多的坑。也會教你如何善用AI輔助開發,但同時培養Debug能力,避免完全依賴工具。讓你從零開始,扎實踏上前端之路。
Thumbnail
此篇文章介紹管理資訊系統(MIS)新手PM必學的資料庫基礎知識,包含關聯式與非關聯式資料庫、SQL 語法、資料庫設計正規化、分散式資料庫、備份與還原等重要概念,並以淺顯易懂的方式說明,適合沒有程式背景的PM快速入門。
Thumbnail
此篇文章介紹管理資訊系統(MIS)新手PM必學的資料庫基礎知識,包含關聯式與非關聯式資料庫、SQL 語法、資料庫設計正規化、分散式資料庫、備份與還原等重要概念,並以淺顯易懂的方式說明,適合沒有程式背景的PM快速入門。
Thumbnail
這篇文章記錄近期學習的技術重點,包含WebStorage & Cookie安全性問題、排序演算法Merge Sort、圖的遍歷DFS,以及React Component開發經驗。文中提供相關學習資源連結,適合對網頁開發、演算法及面試準備感興趣的朋友參考。
Thumbnail
這篇文章記錄近期學習的技術重點,包含WebStorage & Cookie安全性問題、排序演算法Merge Sort、圖的遍歷DFS,以及React Component開發經驗。文中提供相關學習資源連結,適合對網頁開發、演算法及面試準備感興趣的朋友參考。
Thumbnail
本文章提供前端開發的完整知識地圖,涵蓋 JavaScript 基礎概念、進階概念、前端開發基礎、前端框架與工具、系統設計與架構,以及開發工具與實作等面向,並以 SEO 友善的方式撰寫,適合想學習前端開發或準備面試的讀者。
Thumbnail
本文章提供前端開發的完整知識地圖,涵蓋 JavaScript 基礎概念、進階概念、前端開發基礎、前端框架與工具、系統設計與架構,以及開發工具與實作等面向,並以 SEO 友善的方式撰寫,適合想學習前端開發或準備面試的讀者。
Thumbnail
本篇文章介紹了Laravel這個開源PHP框架,重點解析其MVC架構及相關功能,包括中介層、服務層、數據傳輸對象(DTO)與值對象(VO)。Laravel的穩定性與擴展性使其成為臺灣許多企業的首選框架,並提供升級與編碼風格的資源參考,適合所有PHP開發者瞭解和掌握。
Thumbnail
本篇文章介紹了Laravel這個開源PHP框架,重點解析其MVC架構及相關功能,包括中介層、服務層、數據傳輸對象(DTO)與值對象(VO)。Laravel的穩定性與擴展性使其成為臺灣許多企業的首選框架,並提供升級與編碼風格的資源參考,適合所有PHP開發者瞭解和掌握。
Thumbnail
本篇藉由追蹤DRF認證的源碼,幫助初學者能夠更佳理解其相關機制。
Thumbnail
本篇藉由追蹤DRF認證的源碼,幫助初學者能夠更佳理解其相關機制。
Thumbnail
對於想透過DRF來建立RESTfull API的初學者,建立純淨版的項目將有助於了解 DRF 的核心概念,並適合在簡單應用中快速搭建 RESTful API。
Thumbnail
對於想透過DRF來建立RESTfull API的初學者,建立純淨版的項目將有助於了解 DRF 的核心概念,並適合在簡單應用中快速搭建 RESTful API。
Thumbnail
在前端開發中,有許多專有名詞需要掌握,特別是關於渲染方式和應用架構。本文將介紹SSR、CSR、MPA 及 SPA 。
Thumbnail
在前端開發中,有許多專有名詞需要掌握,特別是關於渲染方式和應用架構。本文將介紹SSR、CSR、MPA 及 SPA 。
追蹤感興趣的內容從 Google News 追蹤更多 vocus 的最新精選內容追蹤 Google News