exception.py 2.3 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768
  1. # -*- coding: utf-8 -*-
  2. """
  3. @author: Allen
  4. @Created on: 2023/10/18
  5. @Remark: 自定义异常处理
  6. """
  7. import logging
  8. import traceback
  9. from django.db.models import ProtectedError, RestrictedError
  10. from django.http import Http404
  11. from rest_framework.exceptions import APIException as DRFAPIException, AuthenticationFailed, PermissionDenied
  12. from rest_framework.status import HTTP_407_PROXY_AUTHENTICATION_REQUIRED, HTTP_401_UNAUTHORIZED
  13. from rest_framework.views import set_rollback, exception_handler
  14. from dvadmin.utils.json_response import ErrorResponse
  15. logger = logging.getLogger(__name__)
  16. def CustomExceptionHandler(ex, context):
  17. """
  18. 统一异常拦截处理
  19. 目的:(1)取消所有的500异常响应,统一响应为标准错误返回
  20. (2)准确显示错误信息
  21. :param ex:
  22. :param context:
  23. :return:
  24. """
  25. msg = ""
  26. code = 4000
  27. # 调用默认的异常处理函数
  28. response = exception_handler(ex, context)
  29. if isinstance(ex, AuthenticationFailed):
  30. # 如果是身份验证错误
  31. if response and response.data.get("detail") == "Given token not valid for any token type":
  32. code = 401
  33. msg = ex.detail
  34. elif response and response.data.get("detail") == "Token is blacklisted":
  35. # token在黑名单
  36. return ErrorResponse(status=HTTP_401_UNAUTHORIZED)
  37. else:
  38. code = 401
  39. msg = ex.detail
  40. elif isinstance(ex, Http404):
  41. code = 400
  42. msg = "接口地址不正确"
  43. elif isinstance(ex, DRFAPIException):
  44. set_rollback()
  45. msg = ex.detail
  46. if isinstance(ex, PermissionDenied):
  47. msg = f'{msg} ({context["request"].method}: {context["request"].path})'
  48. if isinstance(msg, dict):
  49. for k, v in msg.items():
  50. for i in v:
  51. msg = "%s:%s" % (k, i)
  52. elif isinstance(ex, (ProtectedError, RestrictedError)):
  53. set_rollback()
  54. msg = "无法删除:该条数据与其他数据有相关绑定"
  55. # elif isinstance(ex, DatabaseError):
  56. # set_rollback()
  57. # msg = "接口服务器异常,请联系管理员"
  58. elif isinstance(ex, Exception):
  59. logger.exception(traceback.format_exc())
  60. msg = str(ex)
  61. return ErrorResponse(msg=msg, code=code)