Thanks to olau@iola.dk, Suor for the report git-svn-id: http://code.djangoproject.com/svn/django/trunk@11623 bcc190cf-cafb-0310-a4f2-bffc1f526a37
This commit is contained in:
parent
f14833ee67
commit
c161bf21f0
|
@ -2,7 +2,7 @@ from datetime import datetime
|
|||
|
||||
from django.conf import settings
|
||||
from django.contrib.auth.backends import RemoteUserBackend
|
||||
from django.contrib.auth.models import AnonymousUser, User
|
||||
from django.contrib.auth.models import User
|
||||
from django.test import TestCase
|
||||
|
||||
|
||||
|
@ -30,15 +30,15 @@ class RemoteUserTest(TestCase):
|
|||
num_users = User.objects.count()
|
||||
|
||||
response = self.client.get('/remote_user/')
|
||||
self.assert_(isinstance(response.context['user'], AnonymousUser))
|
||||
self.assert_(response.context['user'].is_anonymous())
|
||||
self.assertEqual(User.objects.count(), num_users)
|
||||
|
||||
response = self.client.get('/remote_user/', REMOTE_USER=None)
|
||||
self.assert_(isinstance(response.context['user'], AnonymousUser))
|
||||
self.assert_(response.context['user'].is_anonymous())
|
||||
self.assertEqual(User.objects.count(), num_users)
|
||||
|
||||
response = self.client.get('/remote_user/', REMOTE_USER='')
|
||||
self.assert_(isinstance(response.context['user'], AnonymousUser))
|
||||
self.assert_(response.context['user'].is_anonymous())
|
||||
self.assertEqual(User.objects.count(), num_users)
|
||||
|
||||
def test_unknown_user(self):
|
||||
|
@ -115,7 +115,7 @@ class RemoteUserNoCreateTest(RemoteUserTest):
|
|||
def test_unknown_user(self):
|
||||
num_users = User.objects.count()
|
||||
response = self.client.get('/remote_user/', REMOTE_USER='newuser')
|
||||
self.assert_(isinstance(response.context['user'], AnonymousUser))
|
||||
self.assert_(response.context['user'].is_anonymous())
|
||||
self.assertEqual(User.objects.count(), num_users)
|
||||
|
||||
|
||||
|
|
|
@ -8,6 +8,27 @@ 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()
|
||||
|
||||
def auth(request):
|
||||
"""
|
||||
|
@ -17,15 +38,26 @@ def auth(request):
|
|||
If there is no 'user' attribute in the request, uses AnonymousUser (from
|
||||
django.contrib.auth).
|
||||
"""
|
||||
if hasattr(request, 'user'):
|
||||
user = request.user
|
||||
else:
|
||||
from django.contrib.auth.models import AnonymousUser
|
||||
user = AnonymousUser()
|
||||
# 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()
|
||||
|
||||
return {
|
||||
'user': user,
|
||||
'messages': user.get_and_delete_messages(),
|
||||
'perms': PermWrapper(user),
|
||||
'user': ContextLazyObject(get_user),
|
||||
'messages': lazy(memoize(lambda: get_user().get_and_delete_messages(), {}, 0), list)(),
|
||||
'perms': lazy(lambda: PermWrapper(get_user()), PermWrapper)(),
|
||||
}
|
||||
|
||||
def debug(request):
|
||||
|
@ -79,7 +111,7 @@ class PermWrapper(object):
|
|||
|
||||
def __getitem__(self, module_name):
|
||||
return PermLookupDict(self.user, module_name)
|
||||
|
||||
|
||||
def __iter__(self):
|
||||
# I am large, I contain multitudes.
|
||||
raise TypeError("PermWrapper is not iterable.")
|
||||
|
|
|
@ -0,0 +1,17 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<django-objects version="1.0">
|
||||
<object pk="100" model="auth.user">
|
||||
<field type="CharField" name="username">super</field>
|
||||
<field type="CharField" name="first_name">Super</field>
|
||||
<field type="CharField" name="last_name">User</field>
|
||||
<field type="CharField" name="email">super@example.com</field>
|
||||
<field type="CharField" name="password">sha1$995a3$6011485ea3834267d719b4c801409b8b1ddd0158</field>
|
||||
<field type="BooleanField" name="is_staff">True</field>
|
||||
<field type="BooleanField" name="is_active">True</field>
|
||||
<field type="BooleanField" name="is_superuser">True</field>
|
||||
<field type="DateTimeField" name="last_login">2007-05-30 13:20:10</field>
|
||||
<field type="DateTimeField" name="date_joined">2007-05-30 13:20:10</field>
|
||||
<field to="auth.group" name="groups" rel="ManyToManyRel"></field>
|
||||
<field to="auth.permission" name="user_permissions" rel="ManyToManyRel"></field>
|
||||
</object>
|
||||
</django-objects>
|
|
@ -0,0 +1 @@
|
|||
{{ user }}
|
|
@ -0,0 +1 @@
|
|||
{% for m in messages %}{{ m }}{% endfor %}
|
|
@ -0,0 +1 @@
|
|||
|
|
@ -0,0 +1 @@
|
|||
{% if perms.auth %}Has auth permissions{% endif %}
|
|
@ -0,0 +1 @@
|
|||
{% if session_accessed %}Session accessed{% else %}Session not accessed{% endif %}
|
|
@ -0,0 +1,3 @@
|
|||
unicode: {{ user }}
|
||||
id: {{ user.id }}
|
||||
username: {{ user.username }}
|
|
@ -36,3 +36,46 @@ class RequestContextProcessorTests(TestCase):
|
|||
self.assertContains(response, url)
|
||||
response = self.client.post(url, {'path': '/blah/'})
|
||||
self.assertContains(response, url)
|
||||
|
||||
class AuthContextProcessorTests(TestCase):
|
||||
"""
|
||||
Tests for the ``django.core.context_processors.auth`` processor
|
||||
"""
|
||||
urls = 'regressiontests.context_processors.urls'
|
||||
fixtures = ['context-processors-users.xml']
|
||||
|
||||
def test_session_not_accessed(self):
|
||||
"""
|
||||
Tests that the session is not accessed simply by including
|
||||
the auth context processor
|
||||
"""
|
||||
response = self.client.get('/auth_processor_no_attr_access/')
|
||||
self.assertContains(response, "Session not accessed")
|
||||
|
||||
def test_session_is_accessed(self):
|
||||
"""
|
||||
Tests that the session is accessed if the auth context processor
|
||||
is used and relevant attributes accessed.
|
||||
"""
|
||||
response = self.client.get('/auth_processor_attr_access/')
|
||||
self.assertContains(response, "Session accessed")
|
||||
|
||||
def test_perms_attrs(self):
|
||||
self.client.login(username='super', password='secret')
|
||||
response = self.client.get('/auth_processor_perms/')
|
||||
self.assertContains(response, "Has auth permissions")
|
||||
|
||||
def test_message_attrs(self):
|
||||
self.client.login(username='super', password='secret')
|
||||
response = self.client.get('/auth_processor_messages/')
|
||||
self.assertContains(response, "Message 1")
|
||||
|
||||
def test_user_attrs(self):
|
||||
"""
|
||||
Test that ContextLazyObject wraps objects properly
|
||||
"""
|
||||
self.client.login(username='super', password='secret')
|
||||
response = self.client.get('/auth_processor_user/')
|
||||
self.assertContains(response, "unicode: super")
|
||||
self.assertContains(response, "id: 100")
|
||||
self.assertContains(response, "username: super")
|
||||
|
|
|
@ -5,4 +5,9 @@ import views
|
|||
|
||||
urlpatterns = patterns('',
|
||||
(r'^request_attrs/$', views.request_processor),
|
||||
(r'^auth_processor_no_attr_access/$', views.auth_processor_no_attr_access),
|
||||
(r'^auth_processor_attr_access/$', views.auth_processor_attr_access),
|
||||
(r'^auth_processor_user/$', views.auth_processor_user),
|
||||
(r'^auth_processor_perms/$', views.auth_processor_perms),
|
||||
(r'^auth_processor_messages/$', views.auth_processor_messages),
|
||||
)
|
||||
|
|
|
@ -6,3 +6,29 @@ from django.template.context import RequestContext
|
|||
def request_processor(request):
|
||||
return render_to_response('context_processors/request_attrs.html',
|
||||
RequestContext(request, {}, processors=[context_processors.request]))
|
||||
|
||||
def auth_processor_no_attr_access(request):
|
||||
r1 = render_to_response('context_processors/auth_attrs_no_access.html',
|
||||
RequestContext(request, {}, processors=[context_processors.auth]))
|
||||
# *After* rendering, we check whether the session was accessed
|
||||
return render_to_response('context_processors/auth_attrs_test_access.html',
|
||||
{'session_accessed':request.session.accessed})
|
||||
|
||||
def auth_processor_attr_access(request):
|
||||
r1 = render_to_response('context_processors/auth_attrs_access.html',
|
||||
RequestContext(request, {}, processors=[context_processors.auth]))
|
||||
return render_to_response('context_processors/auth_attrs_test_access.html',
|
||||
{'session_accessed':request.session.accessed})
|
||||
|
||||
def auth_processor_user(request):
|
||||
return render_to_response('context_processors/auth_attrs_user.html',
|
||||
RequestContext(request, {}, processors=[context_processors.auth]))
|
||||
|
||||
def auth_processor_perms(request):
|
||||
return render_to_response('context_processors/auth_attrs_perms.html',
|
||||
RequestContext(request, {}, processors=[context_processors.auth]))
|
||||
|
||||
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]))
|
||||
|
|
Loading…
Reference in New Issue