cache.fetch in Django?

2019-05-26 16:06发布

Does Django caching have a method similar to Rails' cache.fetch? (http://api.rubyonrails.org/classes/ActiveSupport/Cache/Store.html#M001023) The rails cache fetch works like:

cache.fetch("my_key") {
  // return what I want to put in my_key if it is empty
  "some_value"
}

It's useful because it checks the cache, and returns the value of the cache if it is there. If not, it will store "some_value" in the cache, and then return "some_value".

Is there an equivalent of this in Django? If not, what would the Python syntax for this look like if I were to implement such a function?

3条回答
Fickle 薄情
2楼-- · 2019-05-26 16:32

I think the code you would have to write would be like this: (EDIT)

def get_value(param1,param2):
    return "value %s - %s " % (str(param1),str(param2))

def fetch(key,val_function,**kwargs)
    val = cache.get(key)
    if not val:
        val = val_function(**kwargs)
        cache.set(key,val)
    return val

and you would call it like this:

fetch('key',get_value,param1='first',param2='second')
查看更多
做个烂人
3楼-- · 2019-05-26 16:32

Well to get a default value if the key does not exits you can provide a second parameter:

cache.get('key', 'default')

cache.get() can take a default argument. This specifies which value to return if the object doesn't exist in the cache.

To save the default value in cache if the key does not exist, you can provide your custom cache backend. E.g. this extends the db cache backend (but works the same with others):

from django.core.cache.backends import db

class CustomCache(db.CacheClass):

    def get(self, key, default=None):
        result = super(CustomCache, self).get(key, default)

        if result == default:
            self.add(key, default)
            return default

        return result

But I don't think that this adds any value.

Update:
In response to the comment on the other post: Yes it compares the default value with the returned value and if both are equal, the value gets added to the cache. But cache.add only sets the new value if the key is not already in the cache (contrast to cache.set which always overrides):

To add a key only if it doesn't already exist, use the add() method. It takes the same parameters as set(), but it will not attempt to update the cache if the key specified is already present.

查看更多
\"骚年 ilove
4楼-- · 2019-05-26 16:35

Julian's code is quite good but doesn't take positional args (when you want to use sorted() for example). Here's my fix:

def get_value(param1,param2):
    return "value %s - %s " % (str(param1),str(param2))

def fetch(key,val_function, *args, **kwargs)
    val = cache.get(key)
    if not val:
        val = val_function(*args, **kwargs)
        cache.set(key,val)
    return val
查看更多
登录 后发表回答