Fixes #19763 - LocaleMiddleware should check for supported languages in settings.LANGUAGE_CODE
This commit is contained in:
parent
99edbe0e27
commit
8c8f94fe9d
1
AUTHORS
1
AUTHORS
|
@ -328,6 +328,7 @@ answer newbie questions, and generally made Django that much better:
|
|||
Denis Kuzmichyov <kuzmichyov@gmail.com>
|
||||
Panos Laganakos <panos.laganakos@gmail.com>
|
||||
Nick Lane <nick.lane.au@gmail.com>
|
||||
Łukasz Langa <lukasz@langa.pl>
|
||||
Stuart Langridge <http://www.kryogenix.org/>
|
||||
Paul Lanier <planier@google.com>
|
||||
David Larlet <http://david.larlet.fr>
|
||||
|
|
|
@ -187,10 +187,10 @@ def get_language_info(lang_code):
|
|||
try:
|
||||
return LANG_INFO[lang_code]
|
||||
except KeyError:
|
||||
if '-' in lang_code:
|
||||
splited_lang_code = lang_code.split('-')[0]
|
||||
try:
|
||||
return LANG_INFO[splited_lang_code]
|
||||
except KeyError:
|
||||
raise KeyError("Unknown language code %s and %s." % (lang_code, splited_lang_code))
|
||||
if '-' not in lang_code:
|
||||
raise KeyError("Unknown language code %s." % lang_code)
|
||||
generic_lang_code = lang_code.split('-')[0]
|
||||
try:
|
||||
return LANG_INFO[generic_lang_code]
|
||||
except KeyError:
|
||||
raise KeyError("Unknown language code %s and %s." % (lang_code, generic_lang_code))
|
||||
|
|
|
@ -356,6 +356,20 @@ def check_for_language(lang_code):
|
|||
return True
|
||||
return False
|
||||
|
||||
def get_supported_language_variant(lang_code, supported=None):
|
||||
"""
|
||||
Returns the language-code that's listed in supported languages, possibly
|
||||
selecting a more generic variant. Raises LookupError if nothing found.
|
||||
"""
|
||||
if supported is None:
|
||||
from django.conf import settings
|
||||
supported = dict(settings.LANGUAGES)
|
||||
if lang_code and lang_code not in supported:
|
||||
lang_code = lang_code.split('-')[0] # e.g. if fr-ca is not supported fallback to fr
|
||||
if lang_code and lang_code in supported and check_for_language(lang_code):
|
||||
return lang_code
|
||||
raise LookupError(lang_code)
|
||||
|
||||
def get_language_from_path(path, supported=None):
|
||||
"""
|
||||
Returns the language-code if there is a valid language-code
|
||||
|
@ -396,11 +410,10 @@ def get_language_from_request(request, check_path=False):
|
|||
|
||||
lang_code = request.COOKIES.get(settings.LANGUAGE_COOKIE_NAME)
|
||||
|
||||
if lang_code and lang_code not in supported:
|
||||
lang_code = lang_code.split('-')[0] # e.g. if fr-ca is not supported fallback to fr
|
||||
|
||||
if lang_code and lang_code in supported and check_for_language(lang_code):
|
||||
return lang_code
|
||||
try:
|
||||
return get_supported_language_variant(lang_code, supported)
|
||||
except LookupError:
|
||||
pass
|
||||
|
||||
accept = request.META.get('HTTP_ACCEPT_LANGUAGE', '')
|
||||
for accept_lang, unused in parse_accept_lang_header(accept):
|
||||
|
@ -434,6 +447,9 @@ def get_language_from_request(request, check_path=False):
|
|||
_accepted[normalized] = lang
|
||||
return lang
|
||||
|
||||
try:
|
||||
return get_supported_language_variant(settings.LANGUAGE_CODE, supported)
|
||||
except LookupError:
|
||||
return settings.LANGUAGE_CODE
|
||||
|
||||
dot_re = re.compile(r'\S')
|
||||
|
|
|
@ -19,7 +19,7 @@ from django.utils import translation
|
|||
TEMPLATE_DIRS=(
|
||||
os.path.join(os.path.dirname(upath(__file__)), 'templates'),
|
||||
),
|
||||
LANGUAGE_CODE='en',
|
||||
LANGUAGE_CODE='en-us',
|
||||
LANGUAGES=(
|
||||
('nl', 'Dutch'),
|
||||
('en', 'English'),
|
||||
|
@ -171,6 +171,14 @@ class URLRedirectTests(URLTestCaseBase):
|
|||
response = self.client.get(response['location'])
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
def test_pl_pl_redirect(self):
|
||||
# language from outside of the supported LANGUAGES list
|
||||
response = self.client.get('/account/register/', HTTP_ACCEPT_LANGUAGE='pl-pl')
|
||||
self.assertRedirects(response, '/en/account/register/')
|
||||
|
||||
response = self.client.get(response['location'])
|
||||
self.assertEqual(response.status_code, 200)
|
||||
|
||||
|
||||
class URLVaryAcceptLanguageTests(URLTestCaseBase):
|
||||
"""
|
||||
|
|
|
@ -958,7 +958,7 @@ class TestLanguageInfo(TestCase):
|
|||
self.assertEqual(li['bidi'], False)
|
||||
|
||||
def test_unknown_language_code(self):
|
||||
six.assertRaisesRegex(self, KeyError, "Unknown language code '?xx'?.", get_language_info, 'xx-xx')
|
||||
six.assertRaisesRegex(self, KeyError, r"Unknown language code xx\.", get_language_info, 'xx')
|
||||
|
||||
def test_unknown_only_country_code(self):
|
||||
li = get_language_info('de-xx')
|
||||
|
@ -968,7 +968,7 @@ class TestLanguageInfo(TestCase):
|
|||
self.assertEqual(li['bidi'], False)
|
||||
|
||||
def test_unknown_language_code_and_country_code(self):
|
||||
six.assertRaisesRegex(self, KeyError, "Unknown language code '?xx-xx'? and '?xx'?.", get_language_info, 'xx-xx')
|
||||
six.assertRaisesRegex(self, KeyError, r"Unknown language code xx-xx and xx\.", get_language_info, 'xx-xx')
|
||||
|
||||
|
||||
class MultipleLocaleActivationTests(TestCase):
|
||||
|
|
Loading…
Reference in New Issue