From e80636b6683893d40e171745a4ef0a2f1a09cc82 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C5=81ukasz=20Langa?= Date: Sun, 19 May 2013 11:44:46 +0200 Subject: [PATCH] Added TransRealMixin to fix i18n global state pollution in the test suite --- tests/i18n/__init__.py | 17 +++++++++++++++++ tests/i18n/contenttypes/tests.py | 4 +++- tests/i18n/tests.py | 31 +++++++++++++++++++------------ 3 files changed, 39 insertions(+), 13 deletions(-) diff --git a/tests/i18n/__init__.py b/tests/i18n/__init__.py index e69de29bb2..a3e9ce7053 100644 --- a/tests/i18n/__init__.py +++ b/tests/i18n/__init__.py @@ -0,0 +1,17 @@ +from threading import local + + +class TransRealMixin(object): + """This is the only way to reset the translation machinery. Otherwise + the test suite occasionally fails because of global state pollution + between tests.""" + def flush_caches(self): + from django.utils.translation import trans_real + trans_real._translations = {} + trans_real._active = local() + trans_real._default = None + trans_real._accepted = {} + + def tearDown(self): + self.flush_caches() + super(TransRealMixin, self).tearDown() diff --git a/tests/i18n/contenttypes/tests.py b/tests/i18n/contenttypes/tests.py index 5e8a9823e1..cbac9ec5da 100644 --- a/tests/i18n/contenttypes/tests.py +++ b/tests/i18n/contenttypes/tests.py @@ -10,6 +10,8 @@ from django.utils._os import upath from django.utils import six from django.utils import translation +from i18n import TransRealMixin + @override_settings( USE_I18N=True, @@ -22,7 +24,7 @@ from django.utils import translation ('fr', 'French'), ), ) -class ContentTypeTests(TestCase): +class ContentTypeTests(TransRealMixin, TestCase): def test_verbose_name(self): company_type = ContentType.objects.get(app_label='i18n', model='company') with translation.override('en'): diff --git a/tests/i18n/tests.py b/tests/i18n/tests.py index 1b15720c16..137270f830 100644 --- a/tests/i18n/tests.py +++ b/tests/i18n/tests.py @@ -44,6 +44,7 @@ if can_run_compilation_tests: from .commands.compilation import (PoFileTests, PoFileContentsTests, PercentRenderingTests, MultipleLocaleCompilationTests, CompilationErrorHandling) +from . import TransRealMixin from .forms import I18nForm, SelectDateForm, SelectDateWidget, CompanyForm from .models import Company, TestModel @@ -53,7 +54,8 @@ extended_locale_paths = settings.LOCALE_PATHS + ( os.path.join(here, 'other', 'locale'), ) -class TranslationTests(TestCase): + +class TranslationTests(TransRealMixin, TestCase): def test_override(self): activate('de') @@ -335,6 +337,8 @@ class TranslationTests(TestCase): class TranslationThreadSafetyTests(TestCase): + """Specifically not using TransRealMixin here to test threading.""" + def setUp(self): self._old_language = get_language() self._translations = trans_real._translations @@ -365,9 +369,10 @@ class TranslationThreadSafetyTests(TestCase): @override_settings(USE_L10N=True) -class FormattingTests(TestCase): +class FormattingTests(TransRealMixin, TestCase): def setUp(self): + super(FormattingTests, self).setUp() self.n = decimal.Decimal('66666.666') self.f = 99999.999 self.d = datetime.date(2009, 12, 31) @@ -769,9 +774,10 @@ class FormattingTests(TestCase): self.assertEqual(template2.render(context), output2) self.assertEqual(template3.render(context), output3) -class MiscTests(TestCase): +class MiscTests(TransRealMixin, TestCase): def setUp(self): + super(MiscTests, self).setUp() self.rf = RequestFactory() def test_parse_spec_http_header(self): @@ -915,17 +921,15 @@ class MiscTests(TestCase): self.assertEqual(t_plur.render(Context({'percent': 42, 'num': 4})), '%(percent)s% represents 4 objects') -class ResolutionOrderI18NTests(TestCase): +class ResolutionOrderI18NTests(TransRealMixin, TestCase): def setUp(self): - # Okay, this is brutal, but we have no other choice to fully reset - # the translation framework - trans_real._active = local() - trans_real._translations = {} + super(ResolutionOrderI18NTests, self).setUp() activate('de') def tearDown(self): deactivate() + super(ResolutionOrderI18NTests, self).tearDown() def assertUgettext(self, msgid, msgstr): result = ugettext(msgid) @@ -998,15 +1002,17 @@ class TestLanguageInfo(TestCase): six.assertRaisesRegex(self, KeyError, r"Unknown language code xx-xx and xx\.", get_language_info, 'xx-xx') -class MultipleLocaleActivationTests(TestCase): +class MultipleLocaleActivationTests(TransRealMixin, TestCase): """ Tests for template rendering behavior when multiple locales are activated during the lifetime of the same process. """ def setUp(self): + super(MultipleLocaleActivationTests, self).setUp() self._old_language = get_language() def tearDown(self): + super(MultipleLocaleActivationTests, self).tearDown() activate(self._old_language) def test_single_locale_activation(self): @@ -1135,7 +1141,7 @@ class MultipleLocaleActivationTests(TestCase): 'django.middleware.common.CommonMiddleware', ), ) -class LocaleMiddlewareTests(TestCase): +class LocaleMiddlewareTests(TransRealMixin, TestCase): urls = 'i18n.urls' @@ -1157,12 +1163,12 @@ class LocaleMiddlewareTests(TestCase): 'django.middleware.common.CommonMiddleware', ), ) -class CountrySpecificLanguageTests(TestCase): +class CountrySpecificLanguageTests(TransRealMixin, TestCase): urls = 'i18n.urls' def setUp(self): - trans_real._accepted = {} + super(CountrySpecificLanguageTests, self).setUp() self.rf = RequestFactory() def test_check_for_language(self): @@ -1172,6 +1178,7 @@ class CountrySpecificLanguageTests(TestCase): def test_get_language_from_request(self): + # issue 19919 r = self.rf.get('/') r.COOKIES = {} r.META = {'HTTP_ACCEPT_LANGUAGE': 'en-US,en;q=0.8,bg;q=0.6,ru;q=0.4'}