(django)开发环境中如何testing500.html?
我正在使用Django作为一个项目,并且已经在生产中。
在生产环境中,只要发生服务器错误,就会呈现500.html。
如何在开发环境中testing500.html的渲染? 或者我如何在开发中渲染500.html,如果我closuresdebugging,我仍然得到错误,而不是500.html
背景:我包含一些基于页面的页面元素,有些在调用500.html时缺less,希望在开发环境中进行debugging。
我不想关掉DEBUG。 相反,我把下面的代码片段放到了urls.py中:
if settings.DEBUG: urlpatterns += patterns('', (r'^500/$', 'your_custom_view_if_you_wrote_one'), (r'^404/$', 'django.views.generic.simple.direct_to_template', {'template': '404.html'}), )
在上面的代码片段中,错误页面使用自定义视图,但是可以用Django的direct_to_template视图轻松replace它。
现在,您可以通过调用他们的url: http : //example.com/500和http://example.com/404来testing500和404页面;
在Django 1.6 django.views.generic.simple.direct_to_template
不存在了,这些是我对特殊视图的设置:
# urls.py from django.views.generic import TemplateView from django.views.defaults import page_not_found, server_error urlpatterns += [ url(r'^400/$', TemplateView.as_view(template_name='400.html')), url(r'^403/$', TemplateView.as_view(template_name='403.html')), url(r'^404/$', page_not_found), url(r'^500/$', server_error), ]
如果你想使用默认的Django 500视图而不是你的自定义视图:
if settings.DEBUG: urlpatterns += patterns('', (r'^500/$', 'django.views.defaults.server_error'), (r'^404/$', 'django.views.generic.simple.direct_to_template', {'template': '404.html'}), )
继续shanyu的回答 ,在Django 1.3+中使用:
if settings.DEBUG: urlpatterns += patterns('', (r'^500/$', 'django.views.defaults.server_error'), (r'^404/$', 'django.views.defaults.page_not_found'), )
两个debugging设置都是假的吗?
settings.DEBUG = False settings.TEMPLATE_DEBUG = False
您可以简单地在您的主views.py
文件中定义handler404
和handler500
的错误,详见本答案:
https://stackoverflow.com/a/18009660/1913888
这将返回Django路由到该处理程序时所需的错误。 不需要自定义URLconfiguration路由到不同的URL名称。
urls.py
handler500 = 'project.apps.core.views.handler500' handler404 = 'project.apps.core.views.handler404'
views.py
from django.template.loader import get_template from django.template import Context from django.http import HttpResponseServerError, HttpResponseNotFound def handler500(request, template_name='500.html'): t = get_template(template_name) ctx = Context({}) return HttpResponseServerError(t.render(ctx)) def handler404(request, template_name='404.html'): t = get_template(template_name) ctx = Context({}) return HttpResponseNotFound(t.render(ctx))
tests.py
from django.test import TestCase from django.test.client import RequestFactory from project import urls from ..views import handler404, handler500 class TestErrorPages(TestCase): def test_error_handlers(self): self.assertTrue(urls.handler404.endswith('.handler404')) self.assertTrue(urls.handler500.endswith('.handler500')) factory = RequestFactory() request = factory.get('/') response = handler404(request) self.assertEqual(response.status_code, 404) self.assertIn('404 Not Found!!', unicode(response)) response = handler500(request) self.assertEqual(response.status_code, 500) self.assertIn('500 Internal Server Error', unicode(response))
我如何做和testing自定义error handling程序
基于TemplateView
定义自定义View
# views.py from django.views.generic import TemplateView class ErrorHandler(TemplateView): """ Render error template """ error_code = 404 template_name = 'index/error.html' def dispatch(self, request, *args, **kwargs): """ For error on any methods return just GET """ return self.get(request, *args, **kwargs) def get_context_data(self, **kwargs): context = super().get_context_data(**kwargs) context['error_code'] = self.error_code return context def render_to_response(self, context, **response_kwargs): """ Return correct status code """ response_kwargs = response_kwargs or {} response_kwargs.update(status=self.error_code) return super().render_to_response(context, **response_kwargs)
告诉django使用自定义error handling程序
# urls.py from index.views import ErrorHandler # error handing handlers - fly binding for code in (400, 403, 404, 500): vars()['handler{}'.format(code)] = ErrorHandler.as_view(error_code=code)
自定义error handling程序的testing用例
# tests.py from unittest import mock from django.test import TestCase from django.core.exceptions import SuspiciousOperation, PermissionDenied from django.http import Http404 from index import views class ErrorHandlersTestCase(TestCase): """ Check is correct error handlers work """ def raise_(exception): def wrapped(*args, **kwargs): raise exception('Test exception') return wrapped def test_index_page(self): """ Should check is 200 on index page """ response = self.client.get('/') self.assertEqual(response.status_code, 200) self.assertTemplateUsed(response, 'index/index.html') @mock.patch('index.views.IndexView.get', raise_(Http404)) def test_404_page(self): """ Should check is 404 page correct """ response = self.client.get('/') self.assertEqual(response.status_code, 404) self.assertTemplateUsed(response, 'index/error.html') self.assertIn('404 Page not found', response.content.decode('utf-8')) @mock.patch('index.views.IndexView.get', views.ErrorHandler.as_view(error_code=500)) def test_500_page(self): """ Should check is 500 page correct """ response = self.client.get('/') self.assertEqual(response.status_code, 500) self.assertTemplateUsed(response, 'index/error.html') self.assertIn('500 Server Error', response.content.decode('utf-8')) @mock.patch('index.views.IndexView.get', raise_(SuspiciousOperation)) def test_400_page(self): """ Should check is 400 page correct """ response = self.client.get('/') self.assertEqual(response.status_code, 400) self.assertTemplateUsed(response, 'index/error.html') self.assertIn('400 Bad request', response.content.decode('utf-8')) @mock.patch('index.views.IndexView.get', raise_(PermissionDenied)) def test_403_page(self): """ Should check is 403 page correct """ response = self.client.get('/') self.assertEqual(response.status_code, 403) self.assertTemplateUsed(response, 'index/error.html') self.assertIn('403 Permission Denied', response.content.decode('utf-8'))