Author: lukeplant
Date: 2011-12-11 13:04:56 -0800 (Sun, 11 Dec 2011)
New Revision: 17200

Modified:
   django/trunk/django/http/__init__.py
   django/trunk/tests/regressiontests/cache/tests.py
Log:
Fixed #15863 - SimpleCookies are not correctly serialized with the file or 
database cache backends

Thanks to rakuco for the report and for the tests.

Modified: django/trunk/django/http/__init__.py
===================================================================
--- django/trunk/django/http/__init__.py        2011-12-11 12:04:37 UTC (rev 
17199)
+++ django/trunk/django/http/__init__.py        2011-12-11 21:04:56 UTC (rev 
17200)
@@ -587,6 +587,17 @@
     def __getitem__(self, header):
         return self._headers[header.lower()][1]
 
+    def __getstate__(self):
+        # SimpleCookie is not pickeable with pickle.HIGHEST_PROTOCOL, so we
+        # serialise to a string instead
+        state = self.__dict__.copy()
+        state['cookies'] = str(state['cookies'])
+        return state
+
+    def __setstate__(self, state):
+        self.__dict__.update(state)
+        self.cookies = SimpleCookie(self.cookies)
+
     def has_header(self, header):
         """Case-insensitive check for a header."""
         return header.lower() in self._headers

Modified: django/trunk/tests/regressiontests/cache/tests.py
===================================================================
--- django/trunk/tests/regressiontests/cache/tests.py   2011-12-11 12:04:37 UTC 
(rev 17199)
+++ django/trunk/tests/regressiontests/cache/tests.py   2011-12-11 21:04:56 UTC 
(rev 17200)
@@ -176,6 +176,17 @@
 class BaseCacheTests(object):
     # A common set of tests to apply to all cache backends
 
+    def _get_request_cache(self, path):
+        request = HttpRequest()
+        request.META = {
+            'SERVER_NAME': 'testserver',
+            'SERVER_PORT': 80,
+        }
+        request.path = request.path_info = path
+        request._cache_update_cache = True
+        request.method = 'GET'
+        return request
+
     def test_simple(self):
         # Simple cache set/get works
         self.cache.set("key", "value")
@@ -741,6 +752,35 @@
         self.assertEqual(self.custom_key_cache2.get('answer2'), 42)
 
 
+    def test_cache_write_unpickable_object(self):
+        update_middleware = UpdateCacheMiddleware()
+        update_middleware.cache = self.cache
+
+        fetch_middleware = FetchFromCacheMiddleware()
+        fetch_middleware.cache = self.cache
+
+        request = self._get_request_cache('/cache/test')
+        get_cache_data = FetchFromCacheMiddleware().process_request(request)
+        self.assertEqual(get_cache_data, None)
+
+        response = HttpResponse()
+        content = 'Testing cookie serialization.'
+        response.content = content
+        response.set_cookie('foo', 'bar')
+
+        update_middleware.process_response(request, response)
+
+        get_cache_data = fetch_middleware.process_request(request)
+        self.assertNotEqual(get_cache_data, None)
+        self.assertEqual(get_cache_data.content, content)
+        self.assertEqual(get_cache_data.cookies, response.cookies)
+
+        update_middleware.process_response(request, get_cache_data)
+        get_cache_data = fetch_middleware.process_request(request)
+        self.assertNotEqual(get_cache_data, None)
+        self.assertEqual(get_cache_data.content, content)
+        self.assertEqual(get_cache_data.cookies, response.cookies)
+
 def custom_key_func(key, key_prefix, version):
     "A customized cache key function"
     return 'CUSTOM-' + '-'.join([key_prefix, str(version), key])

-- 
You received this message because you are subscribed to the Google Groups 
"Django updates" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to 
[email protected].
For more options, visit this group at 
http://groups.google.com/group/django-updates?hl=en.

Reply via email to