Skip to content

Commit

Permalink
[1.1.X] Fixed #11461: Ensured complete traceback is available on the …
Browse files Browse the repository at this point in the history
…debug page when an exception is encountered during template rendering, even when running on Python 2.6 or higher. Thanks Glenn.

r12725 and r12726 from trunk.


git-svn-id: http://code.djangoproject.com/svn/django/branches/releases/1.1.X@12727 bcc190cf-cafb-0310-a4f2-bffc1f526a37
  • Loading branch information
kmtracey committed Mar 8, 2010
1 parent 9bdfe17 commit 758123a
Show file tree
Hide file tree
Showing 9 changed files with 39 additions and 17 deletions.
15 changes: 1 addition & 14 deletions django/template/__init__.py
Expand Up @@ -103,20 +103,7 @@
invalid_var_format_string = None

class TemplateSyntaxError(Exception):
def __str__(self):
try:
import cStringIO as StringIO
except ImportError:
import StringIO
output = StringIO.StringIO()
output.write(Exception.__str__(self))
# Check if we wrapped an exception and print that too.
if hasattr(self, 'exc_info'):
import traceback
output.write('\n\nOriginal ')
e = self.exc_info
traceback.print_exception(e[0], e[1], e[2], 500, output)
return output.getvalue()
pass

class TemplateDoesNotExist(Exception):
pass
Expand Down
5 changes: 3 additions & 2 deletions django/template/debug.py
Expand Up @@ -75,10 +75,11 @@ def render_node(self, node, context):
raise
except Exception, e:
from sys import exc_info
wrapped = TemplateSyntaxError(u'Caught an exception while rendering: %s' % force_unicode(e, errors='replace'))
wrapped = TemplateSyntaxError(u'Caught %s while rendering: %s' %
(e.__class__.__name__, force_unicode(e, errors='replace')))
wrapped.source = node.source
wrapped.exc_info = exc_info()
raise wrapped
raise wrapped, None, wrapped.exc_info[2]
return result

class DebugVariableNode(VariableNode):
Expand Down
2 changes: 1 addition & 1 deletion tests/regressiontests/templates/tests.py
Expand Up @@ -176,7 +176,7 @@ def test_url_reverse_no_settings_module(self):
except TemplateSyntaxError, e:
# Assert that we are getting the template syntax error and not the
# string encoding error.
self.assertEquals(e.args[0], "Caught an exception while rendering: Reverse for 'will_not_match' with arguments '()' and keyword arguments '{}' not found.")
self.assertEquals(e.args[0], "Caught NoReverseMatch while rendering: Reverse for 'will_not_match' with arguments '()' and keyword arguments '{}' not found.")

settings.SETTINGS_MODULE = old_settings_module
settings.TEMPLATE_DEBUG = old_template_debug
Expand Down
@@ -0,0 +1,2 @@
{% load debugtags %}
{% go_boom arg %}
Empty file.
10 changes: 10 additions & 0 deletions tests/regressiontests/views/templatetags/debugtags.py
@@ -0,0 +1,10 @@
from django import template

from regressiontests.views import BrokenException

register = template.Library()

@register.simple_tag
def go_boom(arg):
raise BrokenException(arg)

16 changes: 16 additions & 0 deletions tests/regressiontests/views/tests/debug.py
@@ -1,17 +1,23 @@
import inspect

from django.conf import settings
from django.core.files.uploadedfile import SimpleUploadedFile
from django.test import TestCase
from django.core.urlresolvers import reverse
from django.template import TemplateSyntaxError

from regressiontests.views import BrokenException, except_args

class DebugViewTests(TestCase):
def setUp(self):
self.old_debug = settings.DEBUG
settings.DEBUG = True
self.old_template_debug = settings.TEMPLATE_DEBUG
settings.TEMPLATE_DEBUG = True

def tearDown(self):
settings.DEBUG = self.old_debug
settings.TEMPLATE_DEBUG = self.old_template_debug

def test_files(self):
response = self.client.get('/views/raises/')
Expand All @@ -33,3 +39,13 @@ def test_view_exceptions(self):
self.assertRaises(BrokenException, self.client.get,
reverse('view_exception', args=(n,)))

def test_template_exceptions(self):
for n in range(len(except_args)):
try:
self.client.get(reverse('template_exception', args=(n,)))
except TemplateSyntaxError, e:
raising_loc = inspect.trace()[-1][-2][0].strip()
self.failIf(raising_loc.find('raise BrokenException') == -1,
"Failed to find 'raise BrokenException' in last frame of traceback, instead found: %s" %
raising_loc)

1 change: 1 addition & 0 deletions tests/regressiontests/views/urls.py
Expand Up @@ -109,4 +109,5 @@

urlpatterns += patterns('regressiontests.views.views',
url(r'view_exception/(?P<n>\d+)/$', 'view_exception', name='view_exception'),
url(r'template_exception/(?P<n>\d+)/$', 'template_exception', name='template_exception'),
)
5 changes: 5 additions & 0 deletions tests/regressiontests/views/views.py
Expand Up @@ -5,6 +5,7 @@
from django.views.debug import technical_500_response
from django.views.generic.create_update import create_object
from django.core.urlresolvers import get_resolver
from django.shortcuts import render_to_response

from regressiontests.views import BrokenException, except_args

Expand Down Expand Up @@ -52,3 +53,7 @@ def redirect(request):
def view_exception(request, n):
raise BrokenException(except_args[int(n)])

def template_exception(request, n):
return render_to_response('debug/template_exception.html',
{'arg': except_args[int(n)]})

0 comments on commit 758123a

Please sign in to comment.