Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Django REST Exceptions

I currently have some code for a view based on the Django REST Framework. Ive been using a customer exception class, but ideally I want to use the inbuilt Django REST exceptions.

From the code below I feel this probably not the best or cleanest way to utilize the REST Framework exceptions to its maximum.

Has anyone got any good examples where they are catching issues and returning them cleanly with the REST built in exceptions ?

class JSONResponse(HttpResponse):     def __init__(self, data, **kwargs):        content = JSONRenderer().render(data)        kwargs['content_type'] = 'application/json'        super(JSONResponse, self).__init__(content, **kwargs)  def queryInput(request):     try:         auth_token = session_id = getAuthHeader(request)         if not auth_token:             return JSONResponse({'detail' : "fail", "error" : "No X-Auth-Token Found", "data" : None}, status=500)          if request.method:             data = JSONParser().parse(request)             serializer = queryInputSerializer(data=data)          if request.method == 'POST':             if serializer.is_valid():                 input= serializer.data["input"]                 fetchData = MainRunner(input=input,auth_token=auth_token)                 main_data = fetchData.main()              if main_data:                 return JSONResponse({'detail' : "success", "error" : None, "data" : main_data}, status=201)          return JSONResponse({'detail' : "Unknown Error","error" : True, "data" : None}, status=500)      except Exception as e:            return JSONResponse({'error' : str(e)},status=500) 
like image 855
felix001 Avatar asked May 29 '15 11:05

felix001


People also ask

How do I handle exceptions in Django REST framework?

You can implement custom exception handling by creating a handler function that converts exceptions raised in your API views into response objects. This allows you to control the style of error responses used by your API.

How do you return an error in DRF?

The easiest way to change the error style through all the view in your application is to always use serializer. is_valid(raise_exception=True) , and then implement a custom exception handler that defines how the error response is created. For a different approach see stackoverflow.com/questions/26943985/…


1 Answers

The Django REST framework provides several built in exceptions, which are mostly subclasses of DRF's APIException.

You can raise exceptions in your view like you normally would in Python:

from rest_framework.exceptions import APIException  def my_view(request):     raise APIException("There was a problem!") 

You could also create your own custom exception by inheriting from APIException and setting status_code and default_detail. Some of the built in ones are: ParseError, AuthenticationFailed, NotAuthenticated, PermissionDenied, NotFound, NotAcceptable, ValidationError, etc.

These will then get converted to a Response by the REST Framework's exception handler. Each exception is associated with a status code that is added to the Response. By default the exception handler is set to the built in handler:

REST_FRAMEWORK = {     'EXCEPTION_HANDLER': 'rest_framework.views.exception_handler' } 

But you can set it to your own custom exception handler if you want to convert the exceptions yourself by changing this in your settings.py file:

REST_FRAMEWORK = {     'EXCEPTION_HANDLER': 'my_project.my_app.utils.custom_exception_handler' } 

And then create the custom handler in that location:

from rest_framework.views import exception_handler  def custom_exception_handler(exc, context):     # Call REST framework's default exception handler first,     # to get the standard error response.     response = exception_handler(exc, context)      # Now add the HTTP status code to the response.     if response is not None:         response.data['status_code'] = response.status_code      return response 
like image 160
emptyflash Avatar answered Oct 02 '22 15:10

emptyflash