threadprefixmodel.py 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  1. from django.core.cache import cache
  2. from django.db import models
  3. from django.utils.datastructures import SortedDict
  4. from misago.signals import (merge_thread, move_forum_content,
  5. move_thread, remove_thread_prefix)
  6. from misago.thread import local
  7. _thread_local = local()
  8. class ThreadPrefixManager(models.Manager):
  9. def flush_cache(self):
  10. cache.delete('threads_prefixes')
  11. def get_cache(self):
  12. try:
  13. return _thread_local.misago_thread_prefixes
  14. except AttributeError:
  15. _thread_local.misago_thread_prefixes = self.make_cache()
  16. return _thread_local.misago_thread_prefixes
  17. def make_cache(self):
  18. raw_prefixes = cache.get('threads_prefixes', 'nada')
  19. if raw_prefixes == 'nada':
  20. raw_prefixes = [p for p in ThreadPrefix.objects.prefetch_related().order_by('name')]
  21. cache.set('threads_prefixes', raw_prefixes, None)
  22. dict_result = SortedDict()
  23. for prefix in raw_prefixes:
  24. dict_result[prefix.pk] = prefix
  25. return dict_result
  26. def forum_prefixes(self, forum):
  27. forum_prefixes = []
  28. for prefix in self.get_cache().values():
  29. if forum in prefix.forums.all():
  30. forum_prefixes.append((prefix.pk, prefix))
  31. return SortedDict(forum_prefixes)
  32. def prefix_in_forum(self, prefix, forum):
  33. forum_prefixes = self.forum_prefixes(forum)
  34. return prefix in forum_prefixes
  35. class ThreadPrefix(models.Model):
  36. forums = models.ManyToManyField('Forum')
  37. name = models.CharField(max_length=255)
  38. slug = models.SlugField(max_length=255)
  39. style = models.CharField(max_length=255)
  40. objects = ThreadPrefixManager()
  41. class Meta:
  42. app_label = 'misago'
  43. def save(self, *args, **kwargs):
  44. ThreadPrefix.objects.flush_cache()
  45. super(ThreadPrefix, self).save(*args, **kwargs)
  46. def delete(self, *args, **kwargs):
  47. ThreadPrefix.objects.flush_cache()
  48. super(ThreadPrefix, self).delete(*args, **kwargs)
  49. def update_forums(self, new_forums):
  50. current_forums = self.forums.all()
  51. removed_forums = []
  52. for forum in current_forums:
  53. if not forum in new_forums:
  54. removed_forums.append(forum)
  55. if removed_forums:
  56. remove_thread_prefix.send(sender=self, forums=removed_forums)
  57. self.forums.clear()
  58. for forum in new_forums:
  59. self.forums.add(forum)
  60. def move_forum_content_handler(sender, **kwargs):
  61. old_forum_prefixes = ThreadPrefix.objects.forum_prefixes(sender)
  62. new_forum_prefixes = ThreadPrefix.objects.forum_prefixes(kwargs['move_to'])
  63. bad_prefixes = list(set(new_forum_prefixes) - set(old_forum_prefixes))
  64. if bad_prefixes:
  65. sender.thread_set.filter(prefix__in=bad_prefixes).update(prefix=None)
  66. move_forum_content.connect(move_forum_content_handler, dispatch_uid="move_forum_threads_prefixes")
  67. def move_thread_handler(sender, **kwargs):
  68. if sender.prefix and not ThreadPrefix.objects.prefix_in_forum(sender.prefix, kwargs['move_to']):
  69. sender.prefix = None
  70. move_thread.connect(move_thread_handler, dispatch_uid="move_thread_prefixes")
  71. def merge_thread_handler(sender, **kwargs):
  72. if kwargs['new_thread'].prefix and not ThreadPrefix.objects.prefix_in_forum(kwargs['new_thread'].prefix, kwargs['new_thread'].forum):
  73. kwargs['new_thread'].prefix = None
  74. merge_thread.connect(merge_thread_handler, dispatch_uid="merge_threads_prefixes")