Fixed #27882 -- Allowed {% cache %} to cache indefinitely.

This commit is contained in:
Bo Marchman 2017-03-15 13:01:21 -04:00 committed by Tim Graham
parent 44f9241c48
commit 7a7b331cd5
3 changed files with 23 additions and 6 deletions

View File

@ -20,10 +20,11 @@ class CacheNode(Node):
expire_time = self.expire_time_var.resolve(context) expire_time = self.expire_time_var.resolve(context)
except VariableDoesNotExist: except VariableDoesNotExist:
raise TemplateSyntaxError('"cache" tag got an unknown variable: %r' % self.expire_time_var.var) raise TemplateSyntaxError('"cache" tag got an unknown variable: %r' % self.expire_time_var.var)
try: if expire_time is not None:
expire_time = int(expire_time) try:
except (ValueError, TypeError): expire_time = int(expire_time)
raise TemplateSyntaxError('"cache" tag got a non-integer timeout value: %r' % expire_time) except (ValueError, TypeError):
raise TemplateSyntaxError('"cache" tag got a non-integer timeout value: %r' % expire_time)
if self.cache_name: if self.cache_name:
try: try:
cache_name = self.cache_name.resolve(context) cache_name = self.cache_name.resolve(context)

View File

@ -659,8 +659,9 @@ the ``cache`` template tag. To give your template access to this tag, put
The ``{% cache %}`` template tag caches the contents of the block for a given The ``{% cache %}`` template tag caches the contents of the block for a given
amount of time. It takes at least two arguments: the cache timeout, in seconds, amount of time. It takes at least two arguments: the cache timeout, in seconds,
and the name to give the cache fragment. The name will be taken as is, do not and the name to give the cache fragment. The fragment is cached forever if
use a variable. For example: timeout is ``None``. The name will be taken as is, do not use a variable. For
example:
.. code-block:: html+django .. code-block:: html+django
@ -669,6 +670,10 @@ use a variable. For example:
.. sidebar .. .. sidebar ..
{% endcache %} {% endcache %}
.. versionchanged:: 2.0
Older versions don't allow a ``None`` timeout.
Sometimes you might want to cache multiple copies of a fragment depending on Sometimes you might want to cache multiple copies of a fragment depending on
some dynamic data that appears inside the fragment. For example, you might want a some dynamic data that appears inside the fragment. For example, you might want a
separate cached copy of the sidebar used in the previous example for every user separate cached copy of the sidebar used in the previous example for every user

View File

@ -122,6 +122,17 @@ class CacheTagTests(SimpleTestCase):
output = self.engine.render_to_string('cache18') output = self.engine.render_to_string('cache18')
self.assertEqual(output, 'cache18') self.assertEqual(output, 'cache18')
@setup({
'first': '{% load cache %}{% cache None fragment19 %}content{% endcache %}',
'second': '{% load cache %}{% cache None fragment19 %}not rendered{% endcache %}'
})
def test_none_timeout(self):
"""A timeout of None means "cache forever"."""
output = self.engine.render_to_string('first')
self.assertEqual(output, 'content')
output = self.engine.render_to_string('second')
self.assertEqual(output, 'content')
class CacheTests(SimpleTestCase): class CacheTests(SimpleTestCase):