{% cache 300 nums %}
{% for i in nums %}
<p>i</p>
{% endfor %}
{% endcache %}
And assuming we send {'nums': range(100)} from context, then 0 to 99 will be sent in the response.
Now suppose we change context to {'nums': range(1000)}, still for next 5 minutes i.e until the cache expires, 0 to 99 will be sent in the response. 0 to 999 will not be sent in the response.
To fix this, we should use the variable too with the {% cache %} tag. So correct code would be
为了修复这个问题,我们应该使用 {% cache %} 标签。修正的代码为:
{% cache 300 nums_cache nums %}
{% for i in nums %}
<p>i</p>
{% endfor %}
{% endcache %}
After this whenever context nums changes, cache would be reevaluated.
When current user logs out and a new user logs in, still the username of old user is shown on the web page because template fragment is already cached and would not be reevaluated.
Assuming our view uses test.html. Suppose cache is empty now, and you are logged in as user1 and then you make the request to a url which uses test.html. So response will contain <p>user1</p>.
Now if you logout and login as user2 and make the request, still the response will be <p>user1</p> instead of <p>user2</p>.
假如现在你登出去了,然后以登录user2的身份
The reason for this is, as per Django docs.
The extends tag is the key here. It tells the template engine that this template “extends” another template. When the template system evaluates this template, first it locates the parent – in this case, “base.html”.
But in our case, the parent template itself has some cached content, which Django will use. Django will not even bother to look at the {% block body %} of child template if it finds cached content base_body for the parent template.
The fix for this is to differentiate the cache of different users even in the base template. So we could change the base template to look like.
Template fragment caching gotchas
By : Akshar Raaj
Variables in cached template fragment 缓存在模板片段中的变量
Assuming this is in template.
假设模板中包含一下内容。
And assuming we send {'nums': range(100)} from context, then 0 to 99 will be sent in the response.
Now suppose we change context to
{'nums': range(1000)}
, still for next 5 minutes i.e until the cache expires, 0 to 99 will be sent in the response. 0 to 999 will not be sent in the response.To fix this, we should use the variable too with the
{% cache %}
tag. So correct code would be为了修复这个问题,我们应该使用
{% cache %}
标签。修正的代码为:After this whenever context nums changes, cache would be reevaluated.
Boolean variable in cached template fragment
Assuming template contains
and assuming
{'hello': True}
is sent in context. Then<p>Hello</p>
will be sent in response.Now even when we send
{'hello': False}
in context,<p>Hello</p>
will still be sent in response because it's already cached.To fix this.
request.user in cached template fragment
When current user logs out and a new user logs in, still the username of old user is shown on the web page because template fragment is already cached and would not be reevaluated.
在当前用户登出,新用户登录后,之前老用户的用户名仍旧显示在网页上,因为模板片段已经缓存了而且不会再去重新计算。
Fix it like
像这样修正它:
Gotcha while using base template 理解基础模板的使用
Assuming we are using template inheritance, and our base template i.e base.html looks like:
假设我们正在使用模板继承,我们的基本模板,比如 base.html的内容如下:
And the child template, say test.html looks like
另外一个子模板test.html 的内容如下:
Assuming our view uses test.html. Suppose cache is empty now, and you are logged in as user1 and then you make the request to a url which uses test.html. So response will contain
<p>user1</p>
.假设视图使用的是test.html。假定当前缓存是空的,你以user1的身份登录进去,然后去请求一个使用test.html的url。那么,相应将包含
<p>user1</p>
。Now if you logout and login as user2 and make the request, still the response will be
<p>user1</p>
instead of<p>user2</p>
.假如现在你登出去了,然后以登录user2的身份
The reason for this is, as per Django docs.
The extends tag is the key here. It tells the template engine that this template “extends” another template. When the template system evaluates this template, first it locates the parent – in this case, “base.html”.
But in our case, the parent template itself has some cached content, which Django will use. Django will not even bother to look at the
{% block body %}
of child template if it finds cached content base_body for the parent template.The fix for this is to differentiate the cache of different users even in the base template. So we could change the base template to look like.
After this, if user1 is logged in the
<p>user1</p>
is sent in response. If user2 is logged in then<p>user2</p>
is sent in response.Gotcha with {% include %} tag.
It is similar to the gotcha of template inheritance discussed in last section.
Assuming the view uses test.html, which contains.
And body.html contains
So when first user, say user1 logs in, cache is evaluated and
Hello user1
is sent in response. When user2 logs in, stillHello user2
will be sent in response.To fix this, test.html should also use all the variables on which included template depends.
So code in test.html should change to
If included template, i.e body.html depended on any other variable, that other variable too should be used with
{% cache %}
tag.