Package: django-lrucache-backend
A global object cache backend for Django.Set Performance.Delete performance.Aboutlrucache_backendis an in-memory cache that has differing goals to theLocMemCachebackend that Django provides.Originally its purpose was to improve the cache eviction strategy, using an LRU
algorithm over a random cull. However, Django 2.1 changed the LocMemCache to also
use an LRU strategy.Now,lrucache_backendhas two major differences from Django.Eliminates key char validation, improving performance at the cost of not
being portable with memcache backends.Eliminates serialization (pickling), allowing instances to be shared across
requests. Any mutations performed on cache objects are maintained.lrucache_backendfunctions as a global object cache, and uses a familiar Django
interface to avoid poorly reimplementing local object caches in service layers:defget_data_before(self):ifnothasattr(self,'__data'):self.__data=self.expensive_query()returnself.__datadefget_data_after(self):lcache=caches['local']data=lcache.get('our_data')ifnotdata:data=self.expensive_query()lcache.set('our_data',data,timeout=600)returndataThe benefits (despite the longer method) include timeouts, sharing data between
requests, and avoiding network requests. This is especially useful when there
are hundreds or thousands of property accesses that would hit the cache where
network overhead would be prohibitive. TheFat modelpattern can greatly
benefit from tiered caching.Good for?An in memory cache is good for small data that changes rarely. It’s effectively
a global dictionary shared between requests in the same process. Small lookup
tables and database backed settings are good candidates.A small number of keys should be used to avoid engaging the culling strategy
of the cache. Performance goes down fast as soon as the maximum number of keys
are reached, and keys start to evict.This shouldnotbe used as your primary cache, but it makes for an
excellent secondary cache when you want to avoid the overhead of a network call.Use for:Small lookup tablesSettingsBacking store for your service objectsRemembering values for the duration of a request or celery taskSmall global template fragments like sidebars or footersSecondary cacheBad for?An in memory cache is terrible for data that changes often. Because the cache
is process local, it’s extremely difficult to coordinate cache invalidation
from external processes. For that reason, this library does nothing to support
cache invalidation.The cache shares memory with the application, so it’s extremely important to
avoid storing a lot of keys, or any large values.Donotuse for:Instance attributes/propertiesFull templatesTables with a large number of rowsLarge valuesLarge listsPrimary cacheDifferences from LocMemCacheAvoids picklingAvoids key name validationInstallationpipinstalldjango-lrucache-backendRequirementsThere are no longer any external dependencies.lru-dictused to be a dependency,
but as since been replaced with the built inOrderedDictas a consequence of
now deriving from the built inLocMemCache.UsageConfigure yourCACHESDjango setting appropriately:CACHES={'local':{'BACKEND':'lrucache_backend.LRUObjectCache','TIMEOUT':600,'OPTIONS':{'MAX_ENTRIES':100,'CULL_FREQUENCY: 100,},'NAME':'optional-name'}}Note:Set CULL_FREQUENCY == MAX_ENTRIES to only delete a single key per cull to
only eliminate a single entry per cull. This maintains the LRU property most
effectively, but can have performance implications.And then use the cache as you would any other:>>>fromdjango.core.cacheimportcaches>>>local=caches['local']>>>local.set('key',123)>>>local.get('key')...123If you’re going to use this cache backend, then it’s highly recommended to use
it as a non-default cache. That is, do not configure this cache under thedefaultname.Local memory caches compete for memory with your application so it’s in your
best interests to use it as sparingly and deliberately as possible.CompatibilityDjango 2.2+
Python 3.6+LicenceMITAuthorsdjango-lrucache-backendwas written byJosh Smeaton.