From 756cee46d25a52108fd7190f787a7e636962df5d Mon Sep 17 00:00:00 2001 From: Bas Peschier Date: Sat, 7 Mar 2015 13:18:04 +0100 Subject: [PATCH] Fixed #24455 -- Fixed crash in debug view with lazy objects --- django/views/debug.py | 10 ++++++++- tests/view_tests/tests/test_debug.py | 31 ++++++++++++++++++++++++++++ 2 files changed, 40 insertions(+), 1 deletion(-) diff --git a/django/views/debug.py b/django/views/debug.py index 15da162493..d0235f4bd4 100644 --- a/django/views/debug.py +++ b/django/views/debug.py @@ -186,7 +186,15 @@ class SafeExceptionReporterFilter(ExceptionReporterFilter): return request.POST def cleanse_special_types(self, request, value): - if isinstance(value, HttpRequest): + try: + # If value is lazy or a complex object of another kind, this check + # might raise an exception. isinstance checks that lazy HttpRequests + # or MultiValueDicts will have a return value. + is_request = isinstance(value, HttpRequest) + except Exception as e: + return '{!r} while evaluating {!r}'.format(e, value) + + if is_request: # Cleanse the request's POST parameters. value = self.get_request_repr(value) elif isinstance(value, MultiValueDict): diff --git a/tests/view_tests/tests/test_debug.py b/tests/view_tests/tests/test_debug.py index 30dd3a90ad..51f86f225f 100644 --- a/tests/view_tests/tests/test_debug.py +++ b/tests/view_tests/tests/test_debug.py @@ -18,6 +18,7 @@ from django.template.base import TemplateDoesNotExist from django.test import RequestFactory, TestCase, override_settings from django.utils import six from django.utils.encoding import force_bytes, force_text +from django.utils.functional import SimpleLazyObject from django.views.debug import CallableSettingWrapper, ExceptionReporter from .. import BrokenException, except_args @@ -380,6 +381,36 @@ class ExceptionReporterTests(TestCase): html = reporter.get_traceback_html() self.assertIn('

ImportError at /test_view/

', html) + def test_ignore_traceback_evaluation_exceptions(self): + """ + Don't trip over exceptions generated by crafted objects when + evaluating them while cleansing (#24455). + """ + class BrokenEvaluation(Exception): + pass + + def broken_setup(): + raise BrokenEvaluation + + request = self.rf.get('/test_view/') + broken_lazy = SimpleLazyObject(broken_setup) + try: + bool(broken_lazy) + except BrokenEvaluation: + exc_type, exc_value, tb = sys.exc_info() + + reporter = ExceptionReporter(request, exc_type, exc_value, tb) + try: + html = reporter.get_traceback_html() + except BrokenEvaluation: + self.fail("Broken evaluation in traceback is not caught.") + + self.assertIn( + "BrokenEvaluation", + html, + "Evaluation exception reason not mentioned in traceback" + ) + class PlainTextReportTests(TestCase): rf = RequestFactory()