فهرست منبع

feat(api): return status 503 when database is unavailable

Previously, we returned an unspecific 500 error code. Fixes #134.
Nils Wisiol 6 سال پیش
والد
کامیت
7c1b70c4dc
2فایلهای تغییر یافته به همراه30 افزوده شده و 0 حذف شده
  1. 1 0
      api/api/settings.py
  2. 29 0
      api/desecapi/exception_handlers.py

+ 1 - 0
api/api/settings.py

@@ -84,6 +84,7 @@ REST_FRAMEWORK = {
         'rest_framework.parsers.JSONParser',
     ),
     'TEST_REQUEST_DEFAULT_FORMAT': 'json',
+    'EXCEPTION_HANDLER': 'desecapi.exception_handlers.handle_db_unavailable',
 }
 
 # user management configuration

+ 29 - 0
api/desecapi/exception_handlers.py

@@ -0,0 +1,29 @@
+from django.db.utils import OperationalError
+from rest_framework import status
+from rest_framework.response import Response
+from rest_framework.views import exception_handler, set_rollback
+
+
+def handle_db_unavailable(exc, context):
+    """
+    desecapi specific exception handling. If no special treatment is applied,
+    we default to restframework's exception handling. See also
+    https://www.django-rest-framework.org/api-guide/exceptions/#custom-exception-handling
+    """
+
+    if isinstance(exc, OperationalError):
+        if isinstance(exc.args, (list, dict, tuple)) and exc.args and \
+            exc.args[0] in (
+                2002,  # Connection refused (Socket)
+                2003,  # Connection refused (TCP)
+                2005,  # Unresolved host name
+                2007,  # Server protocol mismatch
+                2009,  # Wrong host info
+                2026,  # SSL connection error
+        ):
+            # Gracefully let clients know that we cannot connect to the database
+            data = {'detail': 'Please try again later.'}
+
+            return Response(data, status=status.HTTP_503_SERVICE_UNAVAILABLE)
+
+    return exception_handler(exc, context)