Skip to content

Commit

Permalink
Fix: Request.set_cookie() now accepts expire=datetime/int and max_age…
Browse files Browse the repository at this point in the history
…=timedelta, as documented.
  • Loading branch information
defnull committed Oct 27, 2011
1 parent b230cba commit 80f303c
Show file tree
Hide file tree
Showing 2 changed files with 44 additions and 13 deletions.
25 changes: 18 additions & 7 deletions bottle.py
Expand Up @@ -39,6 +39,7 @@
import warnings

from Cookie import SimpleCookie
from datetime import date as datedate, datetime, timedelta
from tempfile import TemporaryFile
from traceback import format_exc
from urlparse import urljoin, SplitResult as UrlSplitResult
Expand Down Expand Up @@ -851,7 +852,7 @@ def headers(self):
''' A :class:`WSGIHeaderDict` that provides case-insensitive access to
HTTP request headers. '''
return WSGIHeaderDict(self.environ)

def get_header(self, name, default=None):
''' Return the value of a request header, or a given default value. '''
return self.headers.get(name, default)
Expand Down Expand Up @@ -1309,11 +1310,11 @@ def COOKIES(self):
self._cookies = SimpleCookie()
return self._cookies

def set_cookie(self, key, value, secret=None, **options):
def set_cookie(self, name, value, secret=None, **options):
''' Create a new cookie or replace an old one. If the `secret` parameter is
set, create a `Signed Cookie` (described below).
:param key: the name of the cookie.
:param name: the name of the cookie.
:param value: the value of the cookie.
:param secret: a signature key required for signed cookies.
Expand Down Expand Up @@ -1346,14 +1347,24 @@ def set_cookie(self, key, value, secret=None, **options):
self._cookies = SimpleCookie()

if secret:
value = touni(cookie_encode((key, value), secret))
value = touni(cookie_encode((name, value), secret))
elif not isinstance(value, basestring):
raise TypeError('Secret key missing for non-string Cookie.')

if len(value) > 4096: raise ValueError('Cookie value to long.')
self._cookies[key] = value
for k, v in options.iteritems():
self._cookies[key][k.replace('_', '-')] = v
self._cookies[name] = value

for key, value in options.iteritems():
if key == 'max_age':
if isinstance(value, timedelta):
value = value.seconds + value.days * 24 * 3600
if key == 'expires':
if isinstance(value, (datedate, datetime)):
value = value.timetuple()
elif isinstance(value, (int, float)):
value = time.gmtime(value)
value = time.strftime("%a, %d %b %Y %H:%M:%S GMT", value)
self._cookies[name][key.replace('_', '-')] = value

def delete_cookie(self, key, **kwargs):
''' Delete a cookie. Be sure to use the same `domain` and `path`
Expand Down
32 changes: 26 additions & 6 deletions test/test_environ.py
Expand Up @@ -452,14 +452,34 @@ def test_charset(self):
self.assertEqual(rs.charset, 'UTF-8')

def test_set_cookie(self):
response = BaseResponse()
response.set_cookie('name', 'value', max_age=5)
response.set_cookie('name2', 'value 2', path='/foo')
cookies = [value for name, value in response.wsgiheader()
r = BaseResponse()
r.set_cookie('name1', 'value', max_age=5)
r.set_cookie('name2', 'value 2', path='/foo')
cookies = [value for name, value in r.headerlist
if name.title() == 'Set-Cookie']
cookies.sort()
self.assertTrue(cookies[0], 'name=value; Max-Age=5')
self.assertTrue(cookies[1], 'name2="value 2"; Path=/foo')
self.assertEqual(cookies[0], 'name1=value; Max-Age=5')
self.assertEqual(cookies[1], 'name2="value 2"; Path=/foo')

def test_set_cookie_maxage(self):
import datetime
r = BaseResponse()
r.set_cookie('name1', 'value', max_age=5)
r.set_cookie('name2', 'value', max_age=datetime.timedelta(days=1))
cookies = sorted([value for name, value in r.headerlist
if name.title() == 'Set-Cookie'])
self.assertEqual(cookies[0], 'name1=value; Max-Age=5')
self.assertEqual(cookies[1], 'name2=value; Max-Age=86400')

def test_set_cookie_expires(self):
import datetime
r = BaseResponse()
r.set_cookie('name1', 'value', expires=42)
r.set_cookie('name2', 'value', expires=datetime.datetime(1970,1,1,0,0,43))
cookies = sorted([value for name, value in r.headerlist
if name.title() == 'Set-Cookie'])
self.assertEqual(cookies[0], 'name1=value; expires=Thu, 01 Jan 1970 00:00:42 GMT')
self.assertEqual(cookies[1], 'name2=value; expires=Thu, 01 Jan 1970 00:00:43 GMT')

def test_delete_cookie(self):
response = BaseResponse()
Expand Down

0 comments on commit 80f303c

Please sign in to comment.