如何让Django Admin在内联中缓存选择选项?

时间:2018-06-04 13:11:17

标签: python django python-3.x

使用Django 1.11,Python 3.6

我没有任何运气。我正在尝试优化一个缓慢的Django Admin页面,由于大量select下拉列表和多个内联,这个页面会产生大量重复的SQL查询。

我已尝试使用cacheops库和Redis商店,但根本没有任何内容被缓存,即使我将所有设置为使用'*.*': {'ops': 'all', 'timeout': 60*60},自动缓存。我假设这可能是因为Admin似乎绕过了正常的Django ORM对象。

说到这,我尝试了实现一个使用cachetools库的TTLCache类缓存的定制对象管理器:

from django.db import models
from cachetools import TTLCache, cached

cache = TTLCache(maxsize=100, ttl=3600)

class CacheManager(models.Manager):
    @cached(cache)
    def get(self, *args, **kwargs):
        print("Caching get. args: %r. kwargs: %r" % (args, kwargs))
        return super(CacheManager, self).get(*args, **kwargs)

    @cached(cache)
    def all(self, *args, **kwargs):
        print("Caching all. args: %r. kwargs: %r" % (args, kwargs))
        return super(CacheManager, self).all(*args, **kwargs)

    @cached(cache)
    def filter(self, *args, **kwargs):
        print("Caching filter. args: %r. kwargs: %r" % (args, kwargs))
        return super(CacheManager, self).filter(*args, **kwargs)

    @cached(cache)
    def order_by(self, *args, **kwargs):
        print("Caching order_by. args: %r. kwargs: %r" % (args, kwargs))
        value = super(CacheManager, self).order_by(*args, **kwargs)
        print(value)
        return value

    @cached(cache)
    def first(self, *args, **kwargs):
        print("Caching first. args: %r. kwargs: %r" % (args, kwargs))
        return super(CacheManager, self).first(*args, **kwargs)

然后是我的模特课:

class Role(models.Model):
    date_added = models.DateTimeField(auto_now_add=True)
    date_modified = models.DateTimeField(auto_now=True)
    name = models.CharField(max_length=100, unique=True)

    objects = CacheManager()

    class Admin:
        manager = CacheManager()

这也没有做任何事情。起初我以为管理员没有使用定制对象管理器,但是我发现StackOverflow上的一条注释,添加Admin类与管理器应该修复它 - 但在这种情况下它显然不会,因为在加载时一个具有角色select的管理页面我在日志中得到了这个:

2018-06-04 11:49:06,350 [DEBUG] django.db.backends:(0.003)QUERY ='SELECT [cms_role]。[id],[cms_role]。[date_added],[cms_role]。[ date_modified],[cms_role]。[name] FROM [cms_role] ORDER BY [cms_role]。[name] ASC' - PARAMS =(); ARGS =()

**再跳过20次重复**

2018-06-04 11:49:07,572 [DEBUG] django.db.backends:(0.002)QUERY ='SELECT [cms_role]。[id],[cms_role]。[date_added],[cms_role]。[ date_modified],[cms_role]。[name] FROM [cms_role] ORDER BY [cms_role]。[name] ASC' - PARAMS =(); ARGS =()

超过一秒的重复SQL查询!我怎么阻止它这样做?

1 个答案:

答案 0 :(得分:0)

在cacheops中禁用了admin中的自动缓存。 here对此进行了解释:

  

哦,管理员明确禁用了缓存。

     

这是历史决定,我想知道是否应该在下一个主要版本中将其关闭,但目前情况仍然如此。要缓存管理员,您需要覆盖.get_queryset()方法并自己在queryset上调用.cache()

虽然不确定如何形成各种选择的查询集。