Django请求响应周期中cached_property的失效机制与工作原理咨询
关于Django
cached_property 在请求/响应周期的工作原理 嘿,我来帮你把这个问题掰扯清楚~首先得抓住cached_property的核心本质:它的缓存是绑定在模型实例本身上的,不是全局缓存,也不会跨请求共享。简单说就是,缓存结果跟着实例走,实例没了,缓存也就没了。
在请求/响应周期里的表现
Django的每个HTTP请求都是完全独立的:
- 每次请求到来时,视图函数会重新从数据库查询(或创建)
MyModel的实例(比如obj = MyModel.objects.get(pk=1)),这个实例是全新的,没有任何缓存数据。 - 当你第一次调用
obj.count_friends时,它会执行self.friends_set.count()去数据库查询,然后把结果存在这个实例的缓存里。 - 在同一个请求内,后续再调用
obj.count_friends(比如模板里多次使用,或者视图里再次调用),都会直接返回缓存的结果,不会再去碰数据库。 - 请求处理完成后,这个实例会被Python的垃圾回收机制销毁,对应的缓存也跟着消失。
所以回到你的例子:如果只是在模板里用object.count_friends,每次调用视图(哪怕浏览器缓存已清除),都会重新计算结果——因为每次请求都是全新的实例,第一次调用必然触发数据库查询,相当于“刷新”了结果。你的这个理解完全正确,每次请求的数据库查询都会重新执行(第一次调用属性时)。
哪些场景下不会刷新缓存?
主要有两种典型情况:
- 同一个请求内多次调用属性:比如视图里先调用了
obj.count_friends,然后模板里又用了一次,这时候第二次就是用缓存,不会再查数据库。 - 实例未被销毁,且未手动清除缓存时修改了关联数据:比如在同一个请求里,你先调用
obj.count_friends得到结果,然后执行了obj.friends_set.create(...)添加了一个好友,但此时obj.count_friends的缓存还在,再调用它还是旧值,不会自动刷新。如果想要刷新,需要手动删除缓存:del obj.count_friends,之后再调用就会重新执行查询获取最新结果。
另外补充一点:cached_property不会监听数据库的变化,它只是简单地把第一次计算的结果存在实例上,所以只要实例还活着,缓存就一直有效,直到你手动清除或者实例被销毁。
内容的提问来源于stack exchange,提问作者alias51
相关产品推荐
相关产品推荐

