在 Django 中處理全局異常,有幾種常見的方式,通常目標是:
- 捕獲項目中未被單獨處理的錯誤
- 統一返回給前端(如 JSON 響應 / 自定義錯誤頁)
- 方便記錄日志
1. 使用 Django 自帶的全局異常處理機制
Django 有一些內置的全局錯誤視圖(默認在 django.views.defaults
中):
- 404 錯誤:
handler404
- 500 錯誤:
handler500
- 403 錯誤:
handler403
- 400 錯誤:
handler400
你可以在項目的 urls.py 中進行重寫:
# urls.py
from django.conf.urls import handler404, handler500, handler403, handler400
from django.http import JsonResponsedef custom_404(request, exception):return JsonResponse({"error": "頁面未找到"}, status=404)def custom_500(request):return JsonResponse({"error": "服務器錯誤"}, status=500)def custom_403(request, exception):return JsonResponse({"error": "無權限訪問"}, status=403)def custom_400(request, exception):return JsonResponse({"error": "錯誤請求"}, status=400)handler404 = custom_404
handler500 = custom_500
handler403 = custom_403
handler400 = custom_400
👉 適合處理 HTTP 層面的全局錯誤。
2. 使用中間件捕獲全局異常
如果你想在 更底層 捕獲異常,可以寫一個自定義中間件:
# middlewares.py
import logging
from django.http import JsonResponselogger = logging.getLogger(__name__)class GlobalExceptionMiddleware:def __init__(self, get_response):self.get_response = get_responsedef __call__(self, request):try:return self.get_response(request)except Exception as e:logger.error(f"Unhandled Exception: {str(e)}", exc_info=True)return JsonResponse({"error": "服務器內部錯誤"}, status=500)
然后在 settings.py
中注冊:
MIDDLEWARE = [...'your_project.middlewares.GlobalExceptionMiddleware',
]
👉 適合捕獲 所有未被顯式處理的異常,并進行日志記錄 / 統一 JSON 響應。
3. Django REST Framework (DRF) 的全局異常處理
如果你用的是 DRF,可以在 settings.py
中配置全局異常處理函數:
# settings.py
REST_FRAMEWORK = {"EXCEPTION_HANDLER": "your_project.utils.custom_exception_handler"
}
實現 custom_exception_handler
:
# utils.py
from rest_framework.views import exception_handler
from rest_framework.response import Response
from rest_framework import statusdef custom_exception_handler(exc, context):# 先調用 DRF 默認的異常處理response = exception_handler(exc, context)if response is None:# 沒有被 DRF 識別的異常return Response({"error": "服務器內部錯誤"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)# 可以統一改造返回結構return Response({"error": response.data,"status_code": response.status_code}, status=response.status_code)
👉 適合 API 項目,能讓前端統一處理錯誤。
4. 日志系統與監控
全局異常捕獲后,還需要考慮 記錄日志 和 報警。常見做法:
- 在中間件或異常處理函數里調用
logging
,寫到文件或 ELK。 - 接入 Sentry,實時監控線上異常。
? 總結:
- 普通 Django 項目:用 handler404/500/403/400 + 中間件。
- API 項目(DRF):用 自定義 exception_handler。
- 日志監控:結合 logging 或 Sentry。