diff --git a/django/contrib/auth/context_processors.py b/django/contrib/auth/context_processors.py index ad72cd80fc..3ffab01e94 100644 --- a/django/contrib/auth/context_processors.py +++ b/django/contrib/auth/context_processors.py @@ -1,5 +1,3 @@ -from django.utils.functional import lazy, memoize, SimpleLazyObject - # PermWrapper and PermLookupDict proxy the permissions system into objects that # the template system can understand. @@ -36,23 +34,13 @@ def auth(request): If there is no 'user' attribute in the request, uses AnonymousUser (from django.contrib.auth). """ - # If we access request.user, request.session is accessed, which results in - # 'Vary: Cookie' being sent in every request that uses this context - # processor, which can easily be every request on a site if - # TEMPLATE_CONTEXT_PROCESSORS has this context processor added. This kills - # the ability to cache. So, we carefully ensure these attributes are lazy. - # We don't use django.utils.functional.lazy() for User, because that - # requires knowing the class of the object we want to proxy, which could - # break with custom auth backends. LazyObject is a less complete but more - # flexible solution that is a good enough wrapper for 'User'. - def get_user(): - if hasattr(request, 'user'): - return request.user - else: - from django.contrib.auth.models import AnonymousUser - return AnonymousUser() + if hasattr(request, 'user'): + user = request.user + else: + from django.contrib.auth.models import AnonymousUser + user = AnonymousUser() return { - 'user': SimpleLazyObject(get_user), - 'perms': lazy(lambda: PermWrapper(get_user()), PermWrapper)(), + 'user': user, + 'perms': PermWrapper(user), } diff --git a/django/contrib/auth/middleware.py b/django/contrib/auth/middleware.py index 2c19a4e840..1cd8ae5885 100644 --- a/django/contrib/auth/middleware.py +++ b/django/contrib/auth/middleware.py @@ -1,26 +1,21 @@ from django.contrib import auth from django.core.exceptions import ImproperlyConfigured +from django.utils.functional import SimpleLazyObject -class LazyUser(object): - def __get__(self, request, obj_type=None): - if not hasattr(request, '_cached_user'): - from django.contrib.auth import get_user - request._cached_user = get_user(request) - return request._cached_user +def get_user(request): + from django.contrib.auth import get_user + + if not hasattr(request, '_cached_user'): + request._cached_user = get_user(request) + return request._cached_user class AuthenticationMiddleware(object): def process_request(self, request): assert hasattr(request, 'session'), "The Django authentication middleware requires session middleware to be installed. Edit your MIDDLEWARE_CLASSES setting to insert 'django.contrib.sessions.middleware.SessionMiddleware'." - # We dynamically subclass request.__class__ rather than monkey patch the - # original class. - class RequestWithUser(request.__class__): - user = LazyUser() - - request.__class__ = RequestWithUser - return None + request.user = SimpleLazyObject(lambda: get_user(request)) class RemoteUserMiddleware(object): diff --git a/django/utils/functional.py b/django/utils/functional.py index 21463bd575..b0233de6ed 100644 --- a/django/utils/functional.py +++ b/django/utils/functional.py @@ -208,7 +208,7 @@ class LazyObject(object): def __dir__(self): if self._wrapped is None: self._setup() - return dir(self._wrapped) + return dir(self._wrapped) class SimpleLazyObject(LazyObject): """ @@ -227,9 +227,7 @@ class SimpleLazyObject(LazyObject): value. """ self.__dict__['_setupfunc'] = func - # For some reason, we have to inline LazyObject.__init__ here to avoid - # recursion - self._wrapped = None + super(SimpleLazyObject, self).__init__() def __str__(self): if self._wrapped is None: self._setup()