From a2d8acbacda353248fd191b97155cd4cf27dcd66 Mon Sep 17 00:00:00 2001 From: Luke Plant Date: Thu, 15 Oct 2009 14:12:34 +0000 Subject: [PATCH] Fixed a regression on Python 2.6 caused by r11623 This might fix #12037, but I cannot reproduce that bug. Refs #12037 git-svn-id: http://code.djangoproject.com/svn/django/trunk@11625 bcc190cf-cafb-0310-a4f2-bffc1f526a37 --- django/core/context_processors.py | 24 ++-------------- django/utils/functional.py | 28 +++++++++++++++++-- .../context_processors/auth_attrs_user.html | 1 + .../context_processors/tests.py | 4 ++- .../context_processors/urls.py | 1 + .../context_processors/views.py | 3 ++ 6 files changed, 35 insertions(+), 26 deletions(-) diff --git a/django/core/context_processors.py b/django/core/context_processors.py index 707068d3be..0dbd8449b6 100644 --- a/django/core/context_processors.py +++ b/django/core/context_processors.py @@ -8,27 +8,7 @@ RequestContext. """ from django.conf import settings -from django.utils.functional import lazy, memoize, LazyObject - -class ContextLazyObject(LazyObject): - """ - A lazy object initialised from any function, useful for lazily - adding things to the Context. - - Designed for compound objects of unknown type. For simple objects of known - type, use django.utils.functional.lazy. - """ - def __init__(self, func): - """ - Pass in a callable that returns the actual value to be used - """ - self.__dict__['_setupfunc'] = func - # For some reason, we have to inline LazyObject.__init__ here to avoid - # recursion - self._wrapped = None - - def _setup(self): - self._wrapped = self._setupfunc() +from django.utils.functional import lazy, memoize, SimpleLazyObject def auth(request): """ @@ -55,7 +35,7 @@ def auth(request): return AnonymousUser() return { - 'user': ContextLazyObject(get_user), + 'user': SimpleLazyObject(get_user), 'messages': lazy(memoize(lambda: get_user().get_and_delete_messages(), {}, 0), list)(), 'perms': lazy(lambda: PermWrapper(get_user()), PermWrapper)(), } diff --git a/django/utils/functional.py b/django/utils/functional.py index 23614d1712..4fbc8cd630 100644 --- a/django/utils/functional.py +++ b/django/utils/functional.py @@ -257,9 +257,8 @@ class LazyObject(object): A wrapper for another class that can be used to delay instantiation of the wrapped class. - This is useful, for example, if the wrapped class needs to use Django - settings at creation time: we want to permit it to be imported without - accessing settings. + By subclassing, you have the opportunity to intercept and alter the + instantiation. If you don't need to do that, use SimpleLazyObject. """ def __init__(self): self._wrapped = None @@ -287,3 +286,26 @@ class LazyObject(object): """ raise NotImplementedError + +class SimpleLazyObject(LazyObject): + """ + A lazy object initialised from any function. + + Designed for compound objects of unknown type. For builtins or objects of + known type, use django.utils.functional.lazy. + """ + def __init__(self, func): + """ + Pass in a callable that returns the object to be wrapped. + """ + self.__dict__['_setupfunc'] = func + # For some reason, we have to inline LazyObject.__init__ here to avoid + # recursion + self._wrapped = None + + def __str__(self): + if self._wrapped is None: self._setup() + return str(self._wrapped) + + def _setup(self): + self._wrapped = self._setupfunc() diff --git a/tests/regressiontests/context_processors/templates/context_processors/auth_attrs_user.html b/tests/regressiontests/context_processors/templates/context_processors/auth_attrs_user.html index 7ff2c938a2..7ed16d7867 100644 --- a/tests/regressiontests/context_processors/templates/context_processors/auth_attrs_user.html +++ b/tests/regressiontests/context_processors/templates/context_processors/auth_attrs_user.html @@ -1,3 +1,4 @@ unicode: {{ user }} id: {{ user.id }} username: {{ user.username }} +url: {% url userpage user %} diff --git a/tests/regressiontests/context_processors/tests.py b/tests/regressiontests/context_processors/tests.py index a05b143e55..c7fc4e5a93 100644 --- a/tests/regressiontests/context_processors/tests.py +++ b/tests/regressiontests/context_processors/tests.py @@ -4,7 +4,7 @@ Tests for Django's bundled context processors. from django.conf import settings from django.test import TestCase - +from django.template import Template class RequestContextProcessorTests(TestCase): """ @@ -79,3 +79,5 @@ class AuthContextProcessorTests(TestCase): self.assertContains(response, "unicode: super") self.assertContains(response, "id: 100") self.assertContains(response, "username: super") + # bug #12037 is tested by the {% url %} in the template: + self.assertContains(response, "url: /userpage/super/") diff --git a/tests/regressiontests/context_processors/urls.py b/tests/regressiontests/context_processors/urls.py index 45c5fe7777..30728c8df8 100644 --- a/tests/regressiontests/context_processors/urls.py +++ b/tests/regressiontests/context_processors/urls.py @@ -10,4 +10,5 @@ urlpatterns = patterns('', (r'^auth_processor_user/$', views.auth_processor_user), (r'^auth_processor_perms/$', views.auth_processor_perms), (r'^auth_processor_messages/$', views.auth_processor_messages), + url(r'^userpage/(.+)/$', views.userpage, name="userpage"), ) diff --git a/tests/regressiontests/context_processors/views.py b/tests/regressiontests/context_processors/views.py index e5195f9c65..3f2dcb037b 100644 --- a/tests/regressiontests/context_processors/views.py +++ b/tests/regressiontests/context_processors/views.py @@ -32,3 +32,6 @@ def auth_processor_messages(request): request.user.message_set.create(message="Message 1") return render_to_response('context_processors/auth_attrs_messages.html', RequestContext(request, {}, processors=[context_processors.auth])) + +def userpage(request): + pass