使 Django 中的视图缓存过期? [英] Expire a view-cache in Django?

查看:26
本文介绍了使 Django 中的视图缓存过期?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

@cache_page 装饰器 很棒.但是对于我的博客,我想在缓存中保留一个页面,直到有人对帖子发表评论.这听起来是个好主意,因为人们很少发表评论,因此将页面保存在 memcached 中而没有人发表评论会很棒.我在想之前一定有人遇到过这个问题吗?这与按网址缓存不同.

The @cache_page decorator is awesome. But for my blog I would like to keep a page in cache until someone comments on a post. This sounds like a great idea as people rarely comment so keeping the pages in memcached while nobody comments would be great. I'm thinking that someone must have had this problem before? And this is different than caching per url.

所以我想到的解决方案是:

So a solution I'm thinking of is:

@cache_page( 60 * 15, "blog" );
def blog( request ) ...

然后我会保留一个用于博客视图的所有缓存键的列表,然后让博客"缓存空间过期.但我对 Django 的经验并不丰富,所以我想知道是否有人知道这样做的更好方法?

And then I'd keep a list of all cache keys used for the blog view and then have way of expire the "blog" cache space. But I'm not super experienced with Django so I'm wondering if someone knows a better way of doing this?

推荐答案

此解决方案适用于 1.7 之前的 django 版本

这是我写的一个解决方案,用于在我自己的一些项目中执行您所说的操作:

Here's a solution I wrote to do just what you're talking about on some of my own projects:

def expire_view_cache(view_name, args=[], namespace=None, key_prefix=None):
    """
    This function allows you to invalidate any view-level cache. 
        view_name: view function you wish to invalidate or it's named url pattern
        args: any arguments passed to the view function
        namepace: optioal, if an application namespace is needed
        key prefix: for the @cache_page decorator for the function (if any)
    """
    from django.core.urlresolvers import reverse
    from django.http import HttpRequest
    from django.utils.cache import get_cache_key
    from django.core.cache import cache
    # create a fake request object
    request = HttpRequest()
    # Loookup the request path:
    if namespace:
        view_name = namespace + ":" + view_name
    request.path = reverse(view_name, args=args)
    # get cache key, expire if the cached item exists:
    key = get_cache_key(request, key_prefix=key_prefix)
    if key:
        if cache.get(key):
            # Delete the cache entry.  
            #
            # Note that there is a possible race condition here, as another 
            # process / thread may have refreshed the cache between
            # the call to cache.get() above, and the cache.set(key, None) 
            # below.  This may lead to unexpected performance problems under 
            # severe load.
            cache.set(key, None, 0)
        return True
    return False

Django 对视图请求的这些缓存进行键值,因此它的作用是为缓存视图创建一个假请求对象,使用它来获取缓存键,然后使其过期.

Django keys these caches of the view request, so what this does is creates a fake request object for the cached view, uses that to fetch the cache key, then expires it.

要按照您所说的方式使用它,请尝试以下操作:

To use it in the way you're talking about, try something like:

from django.db.models.signals import post_save
from blog.models import Entry

def invalidate_blog_index(sender, **kwargs):
    expire_view_cache("blog")

post_save.connect(invalidate_portfolio_index, sender=Entry)

所以基本上,当一个 blog Entry 对象被保存时,invalidate_blog_index 被调用并且缓存的视图过期.注意:尚未对此进行广泛测试,但到目前为止对我来说效果很好.

So basically, when ever a blog Entry object is saved, invalidate_blog_index is called and the cached view is expired. NB: haven't tested this extensively, but it's worked fine for me so far.

这篇关于使 Django 中的视图缓存过期?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆