1dbcb2999b6a281f624777d32c20b3df30f0182d
[wolnelektury.git] / apps / newtagging / managers.py
1 """
2 Custom managers for Django models registered with the tagging
3 application.
4 """
5 from django.contrib.contenttypes.models import ContentType
6 from django.db import models
7
8
9 class ModelTagManager(models.Manager):
10     """
11     A manager for retrieving tags for a particular model.
12     """
13     def __init__(self, tag_model):
14         super(ModelTagManager, self).__init__()
15         self.tag_model = tag_model
16     
17     def get_query_set(self):
18         content_type = ContentType.objects.get_for_model(self.model)
19         return self.tag_model.objects.filter(
20             items__content_type__pk=content_type.pk).distinct()
21     
22     def related(self, tags, *args, **kwargs):
23         return self.tag_model.objects.related_for_model(tags, self.model, *args, **kwargs)
24     
25     def usage(self, *args, **kwargs):
26         return self.tag_model.objects.usage_for_model(self.model, *args, **kwargs)
27
28
29 class ModelTaggedItemManager(models.Manager):
30     """
31     A manager for retrieving model instances based on their tags.
32     """
33     def __init__(self, tag_model):
34         super(ModelTaggedItemManager, self).__init__()
35         self.intermediary_table_model = tag_model.objects.intermediary_table_model
36
37     def related_to(self, obj, queryset=None, num=None):
38         if queryset is None:
39             return self.intermediary_table_model.objects.get_related(obj, self.model, num=num)
40         else:
41             return self.intermediary_table_model.objects.get_related(obj, queryset, num=num)
42
43     def with_all(self, tags, queryset=None):
44         if queryset is None:
45             return self.intermediary_table_model.objects.get_by_model(self.model, tags)
46         else:
47             return self.intermediary_table_model.objects.get_by_model(queryset, tags)
48
49     def with_any(self, tags, queryset=None):
50         if queryset is None:
51             return self.intermediary_table_model.objects.get_union_by_model(self.model, tags)
52         else:
53             return self.intermediary_table_model.objects.get_union_by_model(queryset, tags)
54
55
56 class TagDescriptor(object):
57     """
58     A descriptor which provides access to a ``ModelTagManager`` for
59     model classes and simple retrieval, updating and deletion of tags
60     for model instances.
61     """
62     def __init__(self, tag_model):
63         self.tag_model = tag_model
64     
65     def __get__(self, instance, owner):
66         if not instance:
67             tag_manager = ModelTagManager(self.tag_model)
68             tag_manager.model = owner
69             return tag_manager
70         else:
71             return self.tag_model.objects.get_for_object(instance)
72
73     def __set__(self, instance, value):
74         self.tag_model.objects.update_tags(instance, value)
75
76     def __del__(self, instance):
77         self.tag_model.objects.update_tags(instance, [])
78