浏览代码

Refs #15902 -- Made set_language() view always set the current language in a cookie.

The plan is to later deprecate/remove storing the language in the session.
Claude Paroz 7 年之前
父节点
当前提交
b3cd9fb18b
共有 3 个文件被更改,包括 23 次插入14 次删除
  1. 9 10
      django/views/i18n.py
  2. 8 4
      docs/topics/i18n/translation.txt
  3. 6 0
      tests/view_tests/tests/test_i18n.py

+ 9 - 10
django/views/i18n.py

@@ -22,9 +22,9 @@ LANGUAGE_QUERY_PARAMETER = 'language'
 
 def set_language(request):
     """
-    Redirect to a given URL while setting the chosen language in the session or
-    cookie. The URL and the language code need to be specified in the request
-    parameters.
+    Redirect to a given URL while setting the chosen language in the session
+    (if enabled) and in a cookie. The URL and the language code need to be
+    specified in the request parameters.
 
     Since this view changes how the user will see the rest of the site, it must
     only be accessed as a POST request. If called as a GET request, it will
@@ -49,13 +49,12 @@ def set_language(request):
                     response = HttpResponseRedirect(next_trans)
             if hasattr(request, 'session'):
                 request.session[LANGUAGE_SESSION_KEY] = lang_code
-            else:
-                response.set_cookie(
-                    settings.LANGUAGE_COOKIE_NAME, lang_code,
-                    max_age=settings.LANGUAGE_COOKIE_AGE,
-                    path=settings.LANGUAGE_COOKIE_PATH,
-                    domain=settings.LANGUAGE_COOKIE_DOMAIN,
-                )
+            response.set_cookie(
+                settings.LANGUAGE_COOKIE_NAME, lang_code,
+                max_age=settings.LANGUAGE_COOKIE_AGE,
+                path=settings.LANGUAGE_COOKIE_PATH,
+                domain=settings.LANGUAGE_COOKIE_DOMAIN,
+            )
     return response
 
 

+ 8 - 4
docs/topics/i18n/translation.txt

@@ -1761,10 +1761,14 @@ Activate this view by adding the following line to your URLconf::
     language-independent itself to work correctly.
 
 The view expects to be called via the ``POST`` method, with a ``language``
-parameter set in request. If session support is enabled, the view
-saves the language choice in the user's session. Otherwise, it saves the
-language choice in a cookie that is by default named ``django_language``.
-(The name can be changed through the :setting:`LANGUAGE_COOKIE_NAME` setting.)
+parameter set in request. If session support is enabled, the view saves the
+language choice in the user's session. It also saves the language choice in a
+cookie that is named ``django_language`` by default. (The name can be changed
+through the :setting:`LANGUAGE_COOKIE_NAME` setting.)
+
+.. versionchanged:: 2.1
+
+    In older versions, the cookie is only set if session support isn't enabled.
 
 After setting the language choice, Django looks for a ``next`` parameter in the
 ``POST`` or ``GET`` data. If that is found and Django considers it to be a safe

+ 6 - 0
tests/view_tests/tests/test_i18n.py

@@ -37,6 +37,12 @@ class SetLanguageTests(TestCase):
         response = self.client.post('/i18n/setlang/', post_data, HTTP_REFERER='/i_should_not_be_used/')
         self.assertRedirects(response, '/')
         self.assertEqual(self.client.session[LANGUAGE_SESSION_KEY], lang_code)
+        # The language is set in a cookie.
+        language_cookie = self.client.cookies[settings.LANGUAGE_COOKIE_NAME]
+        self.assertEqual(language_cookie.value, lang_code)
+        self.assertEqual(language_cookie['domain'], '')
+        self.assertEqual(language_cookie['path'], '/')
+        self.assertEqual(language_cookie['max-age'], '')
 
     def test_setlang_unsafe_next(self):
         """