mirror of
				https://github.com/django/django.git
				synced 2025-10-31 09:41:08 +00:00 
			
		
		
		
	Fixed #21324 -- Translate CSRF failure view
Thanks to Claude Paroz for the original patch.
This commit is contained in:
		
				
					committed by
					
						 Claude Paroz
						Claude Paroz
					
				
			
			
				
	
			
			
			
						parent
						
							090315f5df
						
					
				
				
					commit
					6107435386
				
			| @@ -92,8 +92,7 @@ class CsrfViewMiddleware(object): | ||||
|         return None | ||||
|  | ||||
|     def _reject(self, request, reason): | ||||
|         logger.warning('Forbidden (%s): %s', | ||||
|                        reason, request.path, | ||||
|         logger.warning('Forbidden (%s): %s', reason, request.path, | ||||
|             extra={ | ||||
|                 'status_code': 403, | ||||
|                 'request': request, | ||||
| @@ -184,7 +183,7 @@ class CsrfViewMiddleware(object): | ||||
|             return response | ||||
|  | ||||
|         # If CSRF_COOKIE is unset, then CsrfViewMiddleware.process_view was | ||||
|         # never called, probaby because a request middleware returned a response | ||||
|         # never called, probably because a request middleware returned a response | ||||
|         # (for example, contrib.auth redirecting to a login page). | ||||
|         if request.META.get("CSRF_COOKIE") is None: | ||||
|             return response | ||||
|   | ||||
| @@ -1,11 +1,16 @@ | ||||
| from django.conf import settings | ||||
| from django.http import HttpResponseForbidden | ||||
| from django.template import Context, Template | ||||
| from django.conf import settings | ||||
| from django.utils.translation import ugettext as _ | ||||
|  | ||||
| # We include the template inline since we need to be able to reliably display | ||||
| # this error message, especially for the sake of developers, and there isn't any | ||||
| # other way of making it available independent of what is in the settings file. | ||||
|  | ||||
| # Only the text appearing with DEBUG=False is translated. Normal translation | ||||
| # tags cannot be used with this inline templates as makemessages would not be | ||||
| # able to discover the strings. | ||||
|  | ||||
| CSRF_FAILURE_TEMPLATE = """ | ||||
| <!DOCTYPE html> | ||||
| <html lang="en"> | ||||
| @@ -30,17 +35,11 @@ CSRF_FAILURE_TEMPLATE = """ | ||||
| </head> | ||||
| <body> | ||||
| <div id="summary"> | ||||
|   <h1>Forbidden <span>(403)</span></h1> | ||||
|   <p>CSRF verification failed. Request aborted.</p> | ||||
|   <h1>{{ title }} <span>(403)</span></h1> | ||||
|   <p>{{ main }}</p> | ||||
| {% if no_referer %} | ||||
|   <p>You are seeing this message because this HTTPS site requires a 'Referer | ||||
|    header' to be sent by your Web browser, but none was sent. This header is | ||||
|    required for security reasons, to ensure that your browser is not being | ||||
|    hijacked by third parties.</p> | ||||
|  | ||||
|   <p>If you have configured your browser to disable 'Referer' headers, please | ||||
|    re-enable them, at least for this site, or for HTTPS connections, or for | ||||
|    'same-origin' requests.</p> | ||||
|   <p>{{ no_referer1 }}</p> | ||||
|   <p>{{ no_referer2 }}</p> | ||||
| {% endif %} | ||||
| </div> | ||||
| {% if DEBUG %} | ||||
| @@ -84,21 +83,35 @@ CSRF_FAILURE_TEMPLATE = """ | ||||
| </div> | ||||
| {% else %} | ||||
| <div id="explanation"> | ||||
|   <p><small>More information is available with DEBUG=True.</small></p> | ||||
|   <p><small>{{ more }}</small></p> | ||||
| </div> | ||||
| {% endif %} | ||||
| </body> | ||||
| </html> | ||||
| """ | ||||
|  | ||||
|  | ||||
| def csrf_failure(request, reason=""): | ||||
|     """ | ||||
|     Default view used when request fails CSRF protection | ||||
|     """ | ||||
|     from django.middleware.csrf import REASON_NO_REFERER | ||||
|     t = Template(CSRF_FAILURE_TEMPLATE) | ||||
|     c = Context({'DEBUG': settings.DEBUG, | ||||
|                  'reason': reason, | ||||
|                  'no_referer': reason == REASON_NO_REFERER | ||||
|                  }) | ||||
|     c = Context({ | ||||
|         'title': _("Forbidden"), | ||||
|         'main': _("CSRF verification failed. Request aborted."), | ||||
|         'reason': reason, | ||||
|         'no_referer': reason == REASON_NO_REFERER, | ||||
|         'no_referer1': _( | ||||
|             "You are seeing this message because this HTTPS site requires a " | ||||
|             "'Referer header' to be sent by your Web browser, but none was " | ||||
|             "sent. This header is required for security reasons, to ensure " | ||||
|             "that your browser is not being hijacked by third parties."), | ||||
|         'no_referer2': _( | ||||
|             "If you have configured your browser to disable 'Referer' headers, " | ||||
|             "please re-enable them, at least for this site, or for HTTPS " | ||||
|             "connections, or for 'same-origin' requests."), | ||||
|         'DEBUG': settings.DEBUG, | ||||
|         'more': _("More information is available with DEBUG=True."), | ||||
|     }) | ||||
|     return HttpResponseForbidden(t.render(c), content_type='text/html') | ||||
|   | ||||
							
								
								
									
										
											BIN
										
									
								
								tests/view_tests/locale/nl/LC_MESSAGES/django.mo
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										
											BIN
										
									
								
								tests/view_tests/locale/nl/LC_MESSAGES/django.mo
									
									
									
									
									
										Normal file
									
								
							
										
											Binary file not shown.
										
									
								
							
							
								
								
									
										25
									
								
								tests/view_tests/locale/nl/LC_MESSAGES/django.po
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										25
									
								
								tests/view_tests/locale/nl/LC_MESSAGES/django.po
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,25 @@ | ||||
| # SOME DESCRIPTIVE TITLE. | ||||
| # Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER | ||||
| # This file is distributed under the same license as the PACKAGE package. | ||||
| # FIRST AUTHOR <EMAIL@ADDRESS>, YEAR. | ||||
| # | ||||
| #, fuzzy | ||||
| msgid "" | ||||
| msgstr "" | ||||
| "Project-Id-Version: PACKAGE VERSION\n" | ||||
| "Report-Msgid-Bugs-To: \n" | ||||
| "POT-Creation-Date: 2007-09-15 19:15+0200\n" | ||||
| "PO-Revision-Date: 2010-05-12 12:41-0300\n" | ||||
| "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n" | ||||
| "Language-Team: LANGUAGE <LL@li.org>\n" | ||||
| "MIME-Version: 1.0\n" | ||||
| "Content-Type: text/plain; charset=UTF-8\n" | ||||
| "Content-Transfer-Encoding: 8bit\n" | ||||
|  | ||||
| #: views/csrf.py:98 | ||||
| msgid "Forbidden" | ||||
| msgstr "Verboden" | ||||
|  | ||||
| #: views/csrf.py:99 | ||||
| msgid "CSRF verification failed. Request aborted." | ||||
| msgstr "CSRF-verificatie mislukt. Verzoek afgebroken." | ||||
							
								
								
									
										33
									
								
								tests/view_tests/tests/test_csrf.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										33
									
								
								tests/view_tests/tests/test_csrf.py
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,33 @@ | ||||
| from django.test import TestCase, override_settings, Client | ||||
| from django.utils.translation import override | ||||
|  | ||||
|  | ||||
| class CsrfViewTests(TestCase): | ||||
|     urls = "view_tests.urls" | ||||
|  | ||||
|     @override_settings( | ||||
|         USE_I18N=True, | ||||
|         MIDDLEWARE_CLASSES=( | ||||
|             'django.middleware.locale.LocaleMiddleware', | ||||
|             'django.middleware.common.CommonMiddleware', | ||||
|             'django.middleware.csrf.CsrfViewMiddleware', | ||||
|         ), | ||||
|     ) | ||||
|     def test_translation(self): | ||||
|         """ | ||||
|         Test that an invalid request is rejected with a localized error message. | ||||
|         """ | ||||
|         self.client = Client(enforce_csrf_checks=True) | ||||
|  | ||||
|         response = self.client.post('/', HTTP_HOST='www.example.com') | ||||
|         self.assertContains(response, "Forbidden", status_code=403) | ||||
|         self.assertContains(response, | ||||
|                             "CSRF verification failed. Request aborted.", | ||||
|                             status_code=403) | ||||
|  | ||||
|         with self.settings(LANGUAGE_CODE='nl'), override('en-us'): | ||||
|             response = self.client.post('/', HTTP_HOST='www.example.com') | ||||
|             self.assertContains(response, "Verboden", status_code=403) | ||||
|             self.assertContains(response, | ||||
|                                 "CSRF-verificatie mislukt. Verzoek afgebroken.", | ||||
|                                 status_code=403) | ||||
		Reference in New Issue
	
	Block a user