在Django中缓存“Home Feed”或“News Feed”的最佳做法是什么

时间:2014-10-06 21:25:35

标签: django caching django-cache

我使用Django作为移动前端的API。我只是来回发送JSON。我已经为家庭饲料创建了一个端点。每个用户都有一个独特的家庭饲料,具体取决于他们遵循的人。用户发布了一张照片,并将该照片推送给他们的所有关注者'家庭饲料。到目前为止非常简单直接。

我的几位同事建议我应该实现某种缓存层,但问题是,这不仅仅是一个静态的常规网站。每个视图都是基于访问它的用户动态的。

因此,例如,主页Feed是以DESC顺序(从最近到旧)在平台上发布的照片​​列表。

家庭饲料视图非常基本。每个用户都有一个主页:user_id:%s' Redis中的列表,其中包含照片对象的主键。我通过Redis打电话并抓住request.user的主页提交列表,然后使用该列表查询数据库,如下所示:

homefeed_pk_list = redis_server.lrange('homefeed:user_id:%s' % request.user.pk, 0, 100)

# Home feed queryset
queryset = Photo.objects.filter(pk__in = homefeed_pk_list)
response_data= []
for photo in queryset:
       # Code to return back JSON data
return HttpResponse(json.dumps(response_data), content_type="application/json")    

非常简单。现在我的问题是,在这种情况下缓存的最佳做法应该是什么?我可以单独缓存每个序列化的照片对象并设置24小时的到期时间,因为一些照片对象在多个提要中(用户。如果对象不存在于缓存中,我会点击数据库。你是什么人想到这种方法?

1 个答案:

答案 0 :(得分:1)

为了获得最佳性能,您可以实现类似于Russian Doll Caching的内容,其摘要类似于:缓存对象,这些对象的缓存列表,包含该列表的缓存生成的页面(即,不仅仅是缓存完成的结果,一直缓存。)

但是,举个例子,我可以从:

开始
import hashlib

from django.core.cache import cache
from django.http import HttpResponse

from whereever import redis_server


def feed(request):
    """
    Returns a JSON response containing Photo data.
    """
    # Get the list of PKs from Redis
    photo_pks = redis_server.lrange(
        'homefeed:user_id:%d' % request.user.pk,
        0,
        100
    )

    # Make a SHA1 hash of the PKs (cache key)
    cach_key = hashlib.sha1(unicode(photo_pks)).hexdigest()

    # Get the existing cache
    content = cache.get(cach_key)

    if content is None:
        # Make a queryset of Photos using the PK list
        queryset = Photo.objects.filter(pk__in=photo_pks)

        # Use .values() to get a list of dicts (the response data)
        content = json.dumps(
            queryset.values('pk', 'url', 'spam', 'eggs')
        )

        # Cache the response string for 24 hours
        cache.set(cach_key, content, 60 * 60 * 24)

    return HttpResponse(content, content_type='application/json')

结果将是响应内容将被缓存24小时,或直到Redis中的PK列表(可能在其他地方设置并在添加新照片时更新等)更改,因为缓存键是使用PK列表的哈希值。