Django Rest Framework 全局異常處理

在這里插入圖片描述

在Django Rest Framework(DRF)中,全局異常處理是一種重要的機制,它可以幫助我們更好地管理API中的異常情況,并返回統一的錯誤響應。本文將詳細介紹兩種全局異常處理的方法:使用中間件(Middleware)和使用DRF內置的異常處理機制(ExceptionHandler)。

1. 使用中間件進行異常處理

中間件是Django中的一個通用概念,它可以用于全局性的請求和響應處理。我們可以通過自定義中間件來捕獲API請求中的異常,并返回統一的錯誤響應。

步驟1:配置中間件

首先,在項目的settings.py文件中添加我們自定義的異常處理中間件。

# settings.py
MIDDLEWARE = [# ...# 異常處理中間件'utils.middleware.ExceptionMiddleware',
]

步驟2:自定義中間件

然后,在utils/middleware.py文件中定義我們的異常處理中間件。

# utils/middleware.py
import logging
from django.db import DatabaseError
from django.http.response import JsonResponse
from django.http import HttpResponseServerError
from django.middleware.common import MiddlewareMixin
from rest_framework import status
from rest_framework.response import Response
from utils.enums import *
from utils.exceptions import *
from utils.result import R
logger = logging.getLogger('django')
class ExceptionMiddleware(MiddlewareMixin):"""統一異常處理中間件"""def process_exception(self, request, exception):"""統一異常處理:param request: 請求對象:param exception: 異常對象:return:"""if isinstance(exception, BusinessException):# 業務異常處理data = R.set_result(exception.enum_cls).data()return JsonResponse(data)elif isinstance(exception, DatabaseError):# 數據庫異常r = R.set_result(StatusCodeEnum.DB_ERR)logger.error(r.data(), exc_info=True)return HttpResponseServerError(StatusCodeEnum.SERVER_ERR.errmsg)elif isinstance(exception, Exception):# 服務器異常處理r = R.server_error()logger.error(r.data(), exc_info=True)return HttpResponseServerError(r.errmsg)return None

步驟3:自定義異常類和狀態碼枚舉

utils/exceptions.pyutils/enums.py文件中,我們可以定義自己的異常類和狀態碼枚舉類。

# utils/exceptions.py
class CommonException(Exception):"""公共異常類"""def __init__(self, enum_cls):self.code = enum_cls.codeself.errmsg = enum_cls.errmsgself.enum_cls = enum_cls  # 狀態碼枚舉類super().__init__()
class BusinessException(CommonException):"""業務異常類"""pass
class APIException(CommonException):"""接口異常類"""pass
# utils/enums.py
class StatusCodeEnum(Enum):"""狀態碼枚舉類"""OK = (0, '成功')ERROR = (-1, '錯誤')SERVER_ERR = (500, '服務器異常')# ... 其他狀態碼

步驟4:響應信息封裝

utils/result.py文件中,我們可以定義一個統一項目信息返回結果類。

# utils/result.py
class R(object):"""統一項目信息返回結果類"""def __init__(self):self.code = Noneself.errmsg = Noneself._data = dict()@staticmethoddef ok():"""組織成功響應信息:return:"""r = R()r.code = StatusCodeEnum.OK.coder.errmsg = StatusCodeEnum.OK.errmsgreturn r@staticmethoddef error():"""組織錯誤響應信息:return:"""r = R()r.code = StatusCodeEnum.ERROR.coder.errmsg = StatusCodeEnum.ERROR.errmsgreturn r@staticmethoddef server_error():"""組織服務器錯誤信息:return:"""r = R()r.code = StatusCodeEnum.SERVER_ERR.coder.errmsg = StatusCodeEnum.SERVER_ERR.errmsgreturn r@staticmethoddef set_result(enum):"""組織對應枚舉類的響應信息:param enum: 狀態枚舉類:return:"""r = R()r.code = enum.coder.errmsg = enum.errmsgreturn rdef data(self, key=None, obj=None):"""統一后端返回的數據"""if key:self._data[key] = objcontext = {'code': self.code,'errmsg': self.errmsg,'data':self._data}return context

步驟5:測試視圖

最后,在視圖中拋出我們自定義的異常,以測試我們的異常處理機制是否有效。

# views.py
from rest_framework.decorators import api_view
from rest_framework.views import APIView
from utils.enums import StatusCodeEnum
from utils.exceptions import *
class TestView(APIView):@api_view(['POST'])def verify_params(request):"""校驗注冊信息:param request: 注冊請求對象:return: response_ret"""# 接受參數params = get_parameter_dic(request)username = params.get('username')mobile = params.get('mobile')# 校驗參數all_args = [username, mobile]if not all(all_args):raise BusinessException(StatusCodeEnum.PARAM_ERR)# 用戶名 5-20個字符if not re.match(r'^[a-zA-Z0-9_]{5,20}', username):raise BusinessException(StatusCodeEnum.USER_ERR)# 手機號合法性if not mobile:raise BusinessException(StatusCodeEnum.MOBILE_ERR)return Response("成功", status=status.HTTP_200_OK)

2. 使用ExceptionHandler進行異常處理

除了使用中間件,我們還可以使用DRF內置的異常處理機制(ExceptionHandler)來處理API中的異常。

步驟1:自定義異常處理函數

首先,在utils/exceptions.py文件中定義我們的自定義異常處理函數。

# utils/exceptions.py
from rest_framework.views import exception_handler
def custom_exception_handler(exc, context):response = exception_handler(exc, context)if response is not None:response.data['status_code'] = response.status_codeelif isinstance(exc, Exception):response = Response("其它異常")return response

步驟2:配置ExceptionHandler

然后,在項目的settings.py文件中配置我們自定義的異常處理函數。

# settings.py
REST_FRAMEWORK = {# 統一異常處理'EXCEPTION_HANDLER': 'utils.exception.custom_exception_handler'
}

這樣,當API中發生異常時,就會調用我們自定義的異常處理函數,并返回統一的錯誤響應。
以上就是在Django Rest Framework中進行全局異常處理的兩種方法。我們可以根據項目的具體需求選擇合適的方法來實現異常處理。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/12931.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/12931.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/12931.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

機器學習(3)

目錄 3-1線性回歸 3-2最小二乘解 3-3多元線性回歸 3-4廣義線性模型 3-5對率回歸 3-6對率回歸求解 3-7線性判別分析 3-8LDA的多類推廣 3-9多分類學習基本思路 3-10類別不平衡 3-1線性回歸 線性模型為什么重要? 人類在考慮問題時,通常…

用python寫一個自動生成android開機動畫的工具

要創建一個自動生成Android開機動畫的工具,你需要一些基本的知識,比如Python編程、圖像處理和Android開機動畫的格式。以下是一個簡單的Python腳本示例,它可以生成一個基本的Android開機動畫,具體效果可能需要更多的調整和優化。 …

記錄glide加載圖片,設置圓角

支持所有角的圓角,自動計算合適的半徑,不用擔心圖片比預定值小導致的圓角過大的問題 修改自:https://blog.csdn.net/qq_15059163/article/details/97613790 增加了指定圖片尺寸、解決了圖片某些情況下圓角過大的問題 public class GlideRou…

先有JVM還是先有垃圾回收器?很多人弄混淆了

是先有垃圾回收器再有JVM呢,還是先有JVM再有垃圾回收器呢?或者是先有垃圾回收再有JVM呢?歷史上還真是垃圾回收更早面世,垃圾回收最早起源于1960年誕生的LISP語言,Java只是支持垃圾回收的其中一種。下面我們就來刨析刨析…

外賣系統的JWT實現登錄

1、什么是JWT jwt可以生成一個加密的token,作為用戶登錄的令牌,當用戶登陸成功之后,發放給客戶端。請求需要登錄的資源或者接口的時候,將token攜帶,后端驗證token是否合法。jwt有三部分組成: A:…

【特大喜訊】國內前33位持有PMI-RMP風險管理專業認證的學員分享~!

【學員背景】 沈陽某信息科技有限公司,從事企業采購供應鏈數字化轉型方向; 為企業提供有效的降本增效解決方案。 【學員順利拿證后期訪問】 問:學員您好,首先恭喜您順利拿到RMP證書,請問您在此次備考過程中&#xf…

抖店商品詳情API接口(產品參數|詳情圖)

抖店商品詳情API接口(產品參數|詳情圖) 參數僅供參考: {"code": 0,"msg": "調用成功","time": "1715763239","data": {"properties": [{"format": [{"message": [{&q…

C語言簡要(一)

總得讓她開心吧 helloworld #include <stdio.h>int main() {printf("hello world!\n");return 0; } 程序框架 #include <stdio.h> int main {return 0; }輸出 printf("hello world!\n"); "里面的內容叫做“字符串”&#xff0c;prin…

BUUCTF靶場[MISC]wireshark、被嗅探的流量、神秘龍卷風、另一個世界

[misc]wireshark 考點&#xff1a;流量、追蹤流 工具&#xff1a;wireshark 先看題目&#xff0c;管理員密碼 將下載的文件用wireshark打開&#xff0c;查找flag 點擊追蹤tcp流&#xff0c;開始挨個查看flag [misc]被嗅探的流量 考點&#xff1a;流量、追蹤流 工具&#xf…

武漢星起航:亞馬遜構建綜合性商業生態,賣家買家共享全球化紅利

在當今全球化日益加速的時代&#xff0c;亞馬遜不僅以其卓越的電商平臺服務全球消費者&#xff0c;更通過一系列前沿服務打造了一個綜合性的商業生態系統。在這個生態系統中&#xff0c;賣家能夠輕松拓展全球業務&#xff0c;買家則享受到了前所未有的購物體驗。亞馬遜以其獨特…

FreeRTOS【6】線程優先級

1.開發背景 基于上一篇指引&#xff0c;已經了解了線程的阻塞&#xff0c;這個篇章主要介紹線程優先級的影響 2.開發需求 設計實驗驗證高優先級會搶占低優先級線程 CPU 3.開發環境 window10 MDK STM32F429 FreeRTOS10.3.1 4.實現步驟 1&#xff09;創建測試線程&#xff…

測試之路 - 精準而優雅

引子 這幾年業內一直在做精準測試&#xff0c;大都使用工具 diff 代碼改動、分析代碼覆蓋率這些平臺集成的能力。 業務測試中&#xff0c;我們在技術設計和代碼實現的基礎上也做了一些精減和精準的測試實踐&#xff0c;通過深入測試有針對的設計 case&#xff0c;發現隱藏問題…

抖音小程序使用Vant

安裝 Vant 有針對小程序的版本&#xff0c;通過npm安裝&#xff1a; npm i vant/weapp -S --production構建 npm 安裝 Vant Weapp 后需要構建 NPM&#xff0c;在菜單的【工具】選項中選擇【構建 NPM】&#xff1a; 使用組件 抖音小程序和微信小程序還是有一些差別的&#x…

怎么把3d模型導出cad立面---模大獅模型網

在設計工作中&#xff0c;將3D模型導出到CAD軟件并生成立面圖是一項常見但關鍵的任務。這不僅有助于更好地展示設計方案&#xff0c;還能方便后續的工程制圖和施工。本文將介紹如何通過3ds Max軟件將3D模型導出到CAD軟件&#xff0c;并生成高質量的立面圖&#xff0c;為您提供實…

現貨正泰漏電小型斷路器NXB-32LE-C16 30MA1P+N原裝正品NXB-40L

品牌&#xff1a;CHNT/正泰 型號&#xff1a;NXBLE 額定電流&#xff1a;25A,16A,20A,40A,32A 漏電保護器類型&#xff1a;2P 產地&#xff1a;中國大陸 電壓&#xff1a;1000V及以下 極數&#xff1a;3P,4p,2P,1PN 電源方式&#xff1a;交流電 3C證書編號&#xff1a;…

大模型時代下的先行者:景聯文科技引領數據標注新時代

在大模型時代&#xff0c;數據標注不再是簡單的分類標注&#xff0c;而是一項融合了技術革新、專業技能、法律合規和精細化管理的綜合性任務&#xff0c;對推動AI技術的發展和落地應用具有重要意義。 景聯文科技作為AI基礎行業的數據供應商&#xff0c;可協助人工智能企業解決整…

easyx快速入門1

1.基本說明 EasyX 是針對 C 的圖形庫&#xff0c;可以幫助 C/C 初學者快速上手圖形和游戲編程。 比如&#xff0c;可以基于 EasyX 圖形庫很快的用幾何圖形畫一個房子&#xff0c;或者一輛移動的小車&#xff0c;可以編寫俄羅斯方塊、貪吃蛇、黑白棋等小游戲&#xff0c;可以練…

fl studio試用版文件保存無法打開??一個方法教你免費打開!

前言 當下&#xff0c;各款編曲軟件五花八門&#xff0c;而這其中最有聲譽的必為FL Studio莫屬 這個軟件呢國人習慣叫他水果&#xff0c;擁有強大的錄音、編曲、混音等功能&#xff0c;所以廣受音樂圈歡迎。如今&#xff0c;大部分水果一旦有編曲所需&#xff0c;一般都要使用…

【Python快速上手(二十三)】

目錄 Python快速上手&#xff08;二十三&#xff09;Python3 多線程1. 線程的創建2. 線程同步2.1 鎖&#xff08;Lock&#xff09;2.2 信號量&#xff08;Semaphore&#xff09;2.3 事件&#xff08;Event&#xff09;2.4 條件&#xff08;Condition&#xff09; 3. 線程優先級…

【Linux】Centos9設置ActiveMq開機自啟功能

配置流程&#xff1a; 1. 創建 Systemd 服務文件。這個文件通常存放在/usr/lib/systemd/system/目錄下&#xff0c;命名為 activemq.service。 #先創建文件&#xff0c;然后編輯&#xff1a; sudo touch /usr/lib/systemd/system/activemq.service sudo vim /usr/lib/systemd…