Skip to content

StaticHTMLRenderer cannot handle ValidationError #9209

Closed
@sevdog

Description

@sevdog

Checklist

  • Raised initially as discussion #...
  • This cannot be dealt with as a third party library. (We prefer new functionality to be in the form of third party libraries where possible.)
  • I have reduced the issue to the simplest possible case.

Description

If any ValidationError is raised in a view which is going to use StaticHTMLRenderer then it will cause an error resulting in an Internal-Server-Error because the base class TemplateHTMLRenderer expectes to handle with a dict while in this case it receives a list instead.

def get_template_context(self, data, renderer_context):
response = renderer_context['response']
if response.exception:
data['status_code'] = response.status_code
return data

Code sample

from django.test import TestCase
from rest_framework import exceptions
from rest_framework.renderers import StaticHTMLRenderer
from rest_framework.test import URLPatternsTestCase


class StaticHTMLRendererErrorTests(URLPatternsTestCase):
    class StaticErrorView(APIView):
        renderer_classes = (StaticHTMLRenderer,)

        def get(self, request, **kwargs):
            raise exceptions.ValidationError('error')

    urlpatterns = [path('error', StaticErrorView.as_view())]

    def test_statis_renderer_with_api_exception(self):
        response = self.client.get('/error')  # this line raise a TypeError
        assert response.status_code == 400

Stacktrace

TypeError: list indices must be integers or slices, not str
failed: tests/test_renderers.py:633: in test_statis_renderer_with_api_exception
    response = self.client.get('/error')
.venv/lib/python/site-packages/django/test/client.py:742: in get
    response = super().get(path, data=data, secure=secure, **extra)
.venv/lib/python/site-packages/django/test/client.py:398: in get
    **extra,
.venv/lib/python/site-packages/django/test/client.py:473: in generic
    return self.request(**r)
.venv/lib/python/site-packages/django/test/client.py:714: in request
    response = self.handler(environ)
.venv/lib/python/site-packages/django/test/client.py:145: in __call__
    response = self.get_response(request)
.venv/lib/python/site-packages/django/core/handlers/base.py:130: in get_response
    response = self._middleware_chain(request)
.venv/lib/python/site-packages/django/core/handlers/exception.py:49: in inner
    response = response_for_exception(request, exc)
.venv/lib/python/site-packages/django/core/handlers/exception.py:114: in response_for_exception
    response = handle_uncaught_exception(request, get_resolver(get_urlconf()), sys.exc_info())
.venv/lib/python/site-packages/django/core/handlers/exception.py:47: in inner
    response = get_response(request)
.venv/lib/python/site-packages/django/utils/deprecation.py:117: in __call__
    response = response or self.get_response(request)
.venv/lib/python/site-packages/django/core/handlers/exception.py:49: in inner
    response = response_for_exception(request, exc)
.venv/lib/python/site-packages/django/core/handlers/exception.py:114: in response_for_exception
    response = handle_uncaught_exception(request, get_resolver(get_urlconf()), sys.exc_info())
.venv/lib/python/site-packages/django/core/handlers/exception.py:47: in inner
    response = get_response(request)
.venv/lib/python/site-packages/django/utils/deprecation.py:117: in __call__
    response = response or self.get_response(request)
.venv/lib/python/site-packages/django/core/handlers/exception.py:49: in inner
    response = response_for_exception(request, exc)
.venv/lib/python/site-packages/django/core/handlers/exception.py:114: in response_for_exception
    response = handle_uncaught_exception(request, get_resolver(get_urlconf()), sys.exc_info())
.venv/lib/python/site-packages/django/core/handlers/exception.py:47: in inner
    response = get_response(request)
.venv/lib/python/site-packages/django/utils/deprecation.py:117: in __call__
    response = response or self.get_response(request)
.venv/lib/python/site-packages/django/core/handlers/exception.py:49: in inner
    response = response_for_exception(request, exc)
.venv/lib/python/site-packages/django/core/handlers/exception.py:114: in response_for_exception
    response = handle_uncaught_exception(request, get_resolver(get_urlconf()), sys.exc_info())
.venv/lib/python/site-packages/django/core/handlers/exception.py:47: in inner
    response = get_response(request)
.venv/lib/python/site-packages/django/utils/deprecation.py:117: in __call__
    response = response or self.get_response(request)
.venv/lib/python/site-packages/django/core/handlers/exception.py:49: in inner
    response = response_for_exception(request, exc)
.venv/lib/python/site-packages/django/core/handlers/exception.py:114: in response_for_exception
    response = handle_uncaught_exception(request, get_resolver(get_urlconf()), sys.exc_info())
.venv/lib/python/site-packages/django/core/handlers/exception.py:47: in inner
    response = get_response(request)
.venv/lib/python/site-packages/django/core/handlers/base.py:204: in _get_response
    response = response.render()
.venv/lib/python/site-packages/django/template/response.py:105: in render
    self.content = self.rendered_content
rest_framework/response.py:74: in rendered_content
    ret = renderer.render(self.data, accepted_media_type, context)
rest_framework/renderers.py:232: in render
    context = self.get_template_context(data, renderer_context)
rest_framework/renderers.py:174: in get_template_context
    data['status_code'] = response.status_code
E   TypeError: list indices must be integers or slices, not str

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions