diff options
| author | Étienne Loks <etienne.loks@iggdrasil.net> | 2020-12-01 13:33:21 +0100 | 
|---|---|---|
| committer | Étienne Loks <etienne.loks@iggdrasil.net> | 2021-02-28 12:15:21 +0100 | 
| commit | 5015e03c0ceabe8ca8a7884e7178bfd246d77788 (patch) | |
| tree | f828418edadbf957db52121c13575ed7cc3e068c /archaeological_context_records/models.py | |
| parent | 3c25d1f4ab24a1bea9b4be0757f9b8f243564954 (diff) | |
| download | Ishtar-5015e03c0ceabe8ca8a7884e7178bfd246d77788.tar.bz2 Ishtar-5015e03c0ceabe8ca8a7884e7178bfd246d77788.zip  | |
Context records: show find inside related context records
Diffstat (limited to 'archaeological_context_records/models.py')
| -rw-r--r-- | archaeological_context_records/models.py | 113 | 
1 files changed, 105 insertions, 8 deletions
diff --git a/archaeological_context_records/models.py b/archaeological_context_records/models.py index 0a7cd3d88..8a1011084 100644 --- a/archaeological_context_records/models.py +++ b/archaeological_context_records/models.py @@ -20,6 +20,7 @@  from collections import OrderedDict  import uuid +from django.apps import apps  from django.conf import settings  from django.contrib.gis.db import models  from django.contrib.postgres.indexes import GinIndex @@ -406,7 +407,7 @@ class ContextRecord(BulkUpdatedItem, DocumentItem, BaseHistorizedItem,          'cached_label': 'cached_label__icontains',          'datings__period__label': 'datings__period__label',          'operation_id': 'operation_id', -        'unit__label': "unit__label" +        'unit__label': "unit__label",      }      MANY_COUNTED_FIELDS = ['base_finds']      REVERSED_BOOL_FIELDS = [ @@ -786,6 +787,13 @@ class ContextRecord(BulkUpdatedItem, DocumentItem, BaseHistorizedItem,      def relation_label(self):          return self.label +    def all_base_finds(self): +        BaseFind = apps.get_model("archaeological_finds", "BaseFind") +        ids = [self.id] + [ +            cr.cr_id for cr in ContextRecordTree.objects.filter( +                cr_parent_id=self.id)] +        return BaseFind.objects.filter(context_record_id__in=ids) +      @property      def show_url(self):          return reverse('show-contextrecord', args=[self.pk, '']) @@ -805,7 +813,7 @@ class ContextRecord(BulkUpdatedItem, DocumentItem, BaseHistorizedItem,      @classmethod      def get_query_owns(cls, ishtaruser): -        q = cls._construct_query_own( +        return cls._construct_query_own(              'operation__', Operation._get_query_owns_dicts(ishtaruser)          ) | cls._construct_query_own(              'base_finds__find__basket__', @@ -814,7 +822,6 @@ class ContextRecord(BulkUpdatedItem, DocumentItem, BaseHistorizedItem,              {'history_creator': ishtaruser.user_ptr},              {'operation__end_date__isnull': True}          ]) -        return q      @classmethod      def get_owns(cls, user, menu_filtr=None, limit=None, @@ -855,7 +862,8 @@ class ContextRecord(BulkUpdatedItem, DocumentItem, BaseHistorizedItem,          return self.detailed_related_context_records()      def _get_associated_cached_labels(self): -        from archaeological_finds.models import Find, BaseFind +        BaseFind = apps.get_model("archaeological_finds", "BaseFind") +        Find = apps.get_model("archaeological_finds", "Find")          return list(Find.objects.filter(base_finds__context_record=self).all())\              + list(BaseFind.objects.filter(context_record=self).all()) @@ -932,10 +940,11 @@ class ContextRecord(BulkUpdatedItem, DocumentItem, BaseHistorizedItem,          return q.count()      def detailed_related_context_records(self): -        crs = [] -        for cr in self.right_relations.all(): -            crs.append("{} ({})".format(cr.right_record, -                                         cr.relation_type.get_tiny_label())) +        crs = [ +            "{} ({})".format(cr.right_record, cr.relation_type.get_tiny_label()) +            for cr in self.right_relations.all() +        ] +          return " & ".join(crs)      def find_docs_q(self): @@ -1087,3 +1096,91 @@ class RecordRelationView(models.Model):      def __str__(self):          return "{} \"{}\"".format(self.relation_type, self.right_record) + + +class ContextRecordTree(models.Model): +    CREATE_SQL = """ +    CREATE VIEW cr_parent_relation_id AS +        SELECT id +        FROM archaeological_context_records_relationtype +        WHERE logical_relation in ('included', 'equal'); + +    CREATE VIEW context_records_tree AS +        WITH RECURSIVE rel_tree AS ( +          SELECT cr.id AS cr_id, +                 cr.id AS cr_parent_id, 1 AS level, +                 cr.id || '_' || cr.id || '_1' AS key +            FROM archaeological_context_records_contextrecord cr +         UNION ALL +          SELECT rel.left_record_id AS cr_id, +                 rel.right_record_id AS cr_parent_id, 1 AS level, +                 rel.left_record_id || '_' || rel.right_record_id || '_1' AS key +            FROM archaeological_context_records_recordrelations rel +            WHERE rel.relation_type_id in ( +                SELECT id FROM cr_parent_relation_id +            ) +         UNION ALL +          SELECT p.cr_id AS cr_id, +                 rel.right_record_id AS cr_parent_id, +                 p.level + 1, +                 p.cr_id || '_' || rel.right_record_id || '_' || p.level + 1 AS key +            FROM archaeological_context_records_recordrelations rel, rel_tree p +            WHERE rel.left_record_id = p.cr_parent_id +                  AND rel.relation_type_id in ( +                    SELECT id FROM cr_parent_relation_id +                  ) +                  AND p.level < 10 -- prevent recursive... +        ) +        SELECT DISTINCT key, cr_id, cr_parent_id, level +          FROM rel_tree; + +    CREATE VIEW context_record_tree AS +        SELECT DISTINCT y.key, y.cr_id, y.cr_parent_id +            FROM (SELECT * FROM context_records_tree) y +        ORDER BY y.cr_id, y.cr_parent_id; + +    -- deactivate deletion, update +    CREATE RULE context_records_tree_del AS +        ON DELETE TO context_records_tree +        DO INSTEAD DELETE FROM archaeological_context_records_contextrecord +            WHERE id=NULL; +    CREATE RULE context_record_tree_del AS +        ON DELETE TO context_record_tree +        DO INSTEAD DELETE FROM archaeological_context_records_contextrecord +            WHERE id=NULL; +    CREATE RULE context_records_tree_update AS +        ON UPDATE TO context_records_tree +        DO INSTEAD UPDATE archaeological_context_records_contextrecord +            SET id=id WHERE id=NULL; +    CREATE RULE context_record_tree_update AS +        ON UPDATE TO context_record_tree +        DO INSTEAD UPDATE archaeological_context_records_contextrecord +            SET id=id WHERE id=NULL; +    CREATE RULE context_records_tree_insert AS +        ON INSERT TO context_records_tree +        DO INSTEAD UPDATE archaeological_context_records_contextrecord +            SET id=id WHERE id=NULL; +    CREATE RULE context_record_tree_insert AS +        ON INSERT TO context_record_tree +        DO INSTEAD UPDATE archaeological_context_records_contextrecord +            SET id=id WHERE id=NULL; +    """ +    DELETE_SQL = """ +    DROP VIEW IF EXISTS context_record_tree; +    DROP VIEW IF EXISTS context_records_tree; +    DROP VIEW IF EXISTS cr_parent_relation_id; +    """ +    key = models.TextField(primary_key=True) +    cr = models.ForeignKey( +        "archaeological_context_records.ContextRecord", +        verbose_name=_("Context record"), +        related_name="context_record_tree_parent") +    cr_parent = models.ForeignKey( +        "archaeological_context_records.ContextRecord", +        verbose_name=_("Context record parent"), +        related_name="context_record_tree_child") + +    class Meta: +        managed = False +        db_table = 'context_records_tree' +  | 
