mirror of https://github.com/django/django.git
Added a ``session`` attribute to the test Client, to make it easier to test if session variables have been modified in a view. Also renamed Client.cookie to Client.cookies, to match documentation and common sense.
git-svn-id: http://code.djangoproject.com/svn/django/trunk@4464 bcc190cf-cafb-0310-a4f2-bffc1f526a37
This commit is contained in:
parent
4ccdf127d0
commit
9ba27afce0
|
@ -1,4 +1,5 @@
|
||||||
from cStringIO import StringIO
|
from cStringIO import StringIO
|
||||||
|
from django.conf import settings
|
||||||
from django.core.handlers.base import BaseHandler
|
from django.core.handlers.base import BaseHandler
|
||||||
from django.core.handlers.wsgi import WSGIRequest
|
from django.core.handlers.wsgi import WSGIRequest
|
||||||
from django.dispatch import dispatcher
|
from django.dispatch import dispatcher
|
||||||
|
@ -97,7 +98,8 @@ class Client:
|
||||||
def __init__(self, **defaults):
|
def __init__(self, **defaults):
|
||||||
self.handler = ClientHandler()
|
self.handler = ClientHandler()
|
||||||
self.defaults = defaults
|
self.defaults = defaults
|
||||||
self.cookie = SimpleCookie()
|
self.cookies = SimpleCookie()
|
||||||
|
self.session = {}
|
||||||
|
|
||||||
def request(self, **request):
|
def request(self, **request):
|
||||||
"""
|
"""
|
||||||
|
@ -108,7 +110,7 @@ class Client:
|
||||||
"""
|
"""
|
||||||
|
|
||||||
environ = {
|
environ = {
|
||||||
'HTTP_COOKIE': self.cookie,
|
'HTTP_COOKIE': self.cookies,
|
||||||
'PATH_INFO': '/',
|
'PATH_INFO': '/',
|
||||||
'QUERY_STRING': '',
|
'QUERY_STRING': '',
|
||||||
'REQUEST_METHOD': 'GET',
|
'REQUEST_METHOD': 'GET',
|
||||||
|
@ -141,8 +143,14 @@ class Client:
|
||||||
setattr(response, detail, None)
|
setattr(response, detail, None)
|
||||||
|
|
||||||
if response.cookies:
|
if response.cookies:
|
||||||
self.cookie.update(response.cookies)
|
self.cookies.update(response.cookies)
|
||||||
|
|
||||||
|
if 'django.contrib.sessions' in settings.INSTALLED_APPS:
|
||||||
|
from django.contrib.sessions.middleware import SessionWrapper
|
||||||
|
cookie = self.cookies.get(settings.SESSION_COOKIE_NAME, None)
|
||||||
|
if cookie:
|
||||||
|
self.session = SessionWrapper(cookie.value)
|
||||||
|
|
||||||
return response
|
return response
|
||||||
|
|
||||||
def get(self, path, data={}, **extra):
|
def get(self, path, data={}, **extra):
|
||||||
|
|
|
@ -198,11 +198,6 @@ used as test conditions.
|
||||||
.. _Twill: http://twill.idyll.org/
|
.. _Twill: http://twill.idyll.org/
|
||||||
.. _Selenium: http://www.openqa.org/selenium/
|
.. _Selenium: http://www.openqa.org/selenium/
|
||||||
|
|
||||||
The Test Client is stateful; if a cookie is returned as part of a response,
|
|
||||||
that cookie is provided as part of the next request issued to that Client
|
|
||||||
instance. Expiry policies for these cookies are not followed; if you want
|
|
||||||
a cookie to expire, either delete it manually from ``client.cookies``, or
|
|
||||||
create a new Client instance (which will effectively delete all cookies).
|
|
||||||
|
|
||||||
Making requests
|
Making requests
|
||||||
~~~~~~~~~~~~~~~
|
~~~~~~~~~~~~~~~
|
||||||
|
@ -296,6 +291,33 @@ for testing purposes:
|
||||||
|
|
||||||
.. _RFC2616: http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html
|
.. _RFC2616: http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html
|
||||||
|
|
||||||
|
Persistent state
|
||||||
|
~~~~~~~~~~~~~~~~
|
||||||
|
|
||||||
|
The Test Client is stateful; if a cookie is returned as part of a response,
|
||||||
|
that cookie is provided as part of the next request issued by that Client
|
||||||
|
instance. Expiry policies for these cookies are not followed; if you want
|
||||||
|
a cookie to expire, either delete it manually or create a new Client
|
||||||
|
instance (which will effectively delete all cookies).
|
||||||
|
|
||||||
|
There are two properties of the Test Client which are used to store persistent
|
||||||
|
state information. If necessary, these properties can be interrogated as
|
||||||
|
part of a test condition.
|
||||||
|
|
||||||
|
=============== ==========================================================
|
||||||
|
Property Description
|
||||||
|
=============== ==========================================================
|
||||||
|
``cookies`` A Python ``SimpleCookie`` object, containing the current
|
||||||
|
values of all the client cookies.
|
||||||
|
|
||||||
|
``session`` A dictionary-like object containing session information.
|
||||||
|
See the `session documentation`_ for full details.
|
||||||
|
|
||||||
|
.. _`session documentation`: ../sessions/
|
||||||
|
|
||||||
|
Example
|
||||||
|
~~~~~~~
|
||||||
|
|
||||||
The following is a simple unit test using the Test Client::
|
The following is a simple unit test using the Test Client::
|
||||||
|
|
||||||
import unittest
|
import unittest
|
||||||
|
|
|
@ -99,3 +99,19 @@ class ClientTest(unittest.TestCase):
|
||||||
|
|
||||||
response = self.client.login('/test_client/login_protected_view/', 'otheruser', 'nopassword')
|
response = self.client.login('/test_client/login_protected_view/', 'otheruser', 'nopassword')
|
||||||
self.assertFalse(response)
|
self.assertFalse(response)
|
||||||
|
|
||||||
|
def test_session_modifying_view(self):
|
||||||
|
"Request a page that modifies the session"
|
||||||
|
# Session value isn't set initially
|
||||||
|
try:
|
||||||
|
self.client.session['tobacconist']
|
||||||
|
self.fail("Shouldn't have a session value")
|
||||||
|
except KeyError:
|
||||||
|
pass
|
||||||
|
|
||||||
|
from django.contrib.sessions.models import Session
|
||||||
|
response = self.client.post('/test_client/session_view/')
|
||||||
|
|
||||||
|
# Check that the session was modified
|
||||||
|
self.assertEquals(self.client.session['tobacconist'], 'hovercraft')
|
||||||
|
|
|
@ -6,4 +6,5 @@ urlpatterns = patterns('',
|
||||||
(r'^post_view/$', views.post_view),
|
(r'^post_view/$', views.post_view),
|
||||||
(r'^redirect_view/$', views.redirect_view),
|
(r'^redirect_view/$', views.redirect_view),
|
||||||
(r'^login_protected_view/$', views.login_protected_view),
|
(r'^login_protected_view/$', views.login_protected_view),
|
||||||
|
(r'^session_view/$', views.session_view)
|
||||||
)
|
)
|
||||||
|
|
|
@ -32,4 +32,15 @@ def login_protected_view(request):
|
||||||
c = Context({'user': request.user})
|
c = Context({'user': request.user})
|
||||||
|
|
||||||
return HttpResponse(t.render(c))
|
return HttpResponse(t.render(c))
|
||||||
login_protected_view = login_required(login_protected_view)
|
login_protected_view = login_required(login_protected_view)
|
||||||
|
|
||||||
|
def session_view(request):
|
||||||
|
"A view that modifies the session"
|
||||||
|
|
||||||
|
request.session['tobacconist'] = 'hovercraft'
|
||||||
|
|
||||||
|
t = Template('This is a view that modifies the session.',
|
||||||
|
name='Session Modifying View Template')
|
||||||
|
c = Context()
|
||||||
|
return HttpResponse(t.render(c))
|
||||||
|
|
Loading…
Reference in New Issue