cachebuster.py 2.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697
  1. from django.core.cache import cache as default_cache
  2. from django.db import models
  3. from misago.core import threadstore
  4. CACHE_KEY = 'misago_cachebuster'
  5. class CacheBusterController(object):
  6. def register_cache(self, cache):
  7. from misago.core.models import CacheVersion
  8. CacheVersion.objects.create(cache=cache)
  9. def unregister_cache(self, cache):
  10. from misago.core.models import CacheVersion
  11. try:
  12. cache = CacheVersion.objects.get(cache=cache)
  13. cache.delete()
  14. except CacheVersion.DoesNotExist:
  15. raise ValueError('Cache "%s" is not registered' % cache)
  16. @property
  17. def cache(self):
  18. return self.read_threadstore()
  19. def read_threadstore(self):
  20. data = threadstore.get(CACHE_KEY, 'nada')
  21. if data == 'nada':
  22. data = self.read_cache()
  23. threadstore.set(CACHE_KEY, data)
  24. return data
  25. def read_cache(self):
  26. data = default_cache.get(CACHE_KEY, 'nada')
  27. if data == 'nada':
  28. data = self.read_db()
  29. default_cache.set(CACHE_KEY, data)
  30. return data
  31. def read_db(self):
  32. from misago.core.models import CacheVersion
  33. data = {}
  34. for cache_version in CacheVersion.objects.iterator():
  35. data[cache_version.cache] = cache_version.version
  36. return data
  37. def get_cache_version(self, cache):
  38. try:
  39. return self.cache[cache]
  40. except KeyError:
  41. raise ValueError('Cache "%s" is not registered' % cache)
  42. def is_cache_valid(self, cache, version):
  43. try:
  44. return self.cache[cache] == version
  45. except KeyError:
  46. raise ValueError('Cache "%s" is not registered' % cache)
  47. def invalidate_cache(self, cache):
  48. from misago.core.models import CacheVersion
  49. self.cache[cache] += 1
  50. CacheVersion.objects.filter(cache=cache).update(
  51. version=models.F('version') + 1)
  52. default_cache.delete(CACHE_KEY)
  53. def invalidate_all(self):
  54. from misago.core.models import CacheVersion
  55. CacheVersion.objects.update(version=models.F('version') + 1)
  56. default_cache.delete(CACHE_KEY)
  57. _controller = CacheBusterController()
  58. # Expose controller API
  59. def register(cache):
  60. _controller.register_cache(cache)
  61. def unregister(cache):
  62. _controller.unregister_cache(cache)
  63. def get_version(cache):
  64. return _controller.get_cache_version(cache)
  65. def is_valid(cache, version):
  66. return _controller.is_cache_valid(cache, version)
  67. def invalidate(cache):
  68. _controller.invalidate_cache(cache)
  69. def invalidate_all():
  70. _controller.invalidate_all()