diff options
author | Étienne Loks <etienne.loks@iggdrasil.net> | 2025-03-19 11:54:38 +0100 |
---|---|---|
committer | Étienne Loks <etienne.loks@iggdrasil.net> | 2025-03-19 12:39:22 +0100 |
commit | 3adbd561ced57cb9c950af2d6d7d25f57f8799e0 (patch) | |
tree | e2301ff31a54062c731a60774e088f073d6a89cf | |
parent | 6468fa4c22b5ec2c30b450a5d0f8cc005d01f4be (diff) | |
download | Ishtar-3adbd561ced57cb9c950af2d6d7d25f57f8799e0.tar.bz2 Ishtar-3adbd561ced57cb9c950af2d6d7d25f57f8799e0.zip |
🚑️ fix huge performance problems on permissions when too many items are attached
-rw-r--r-- | archaeological_context_records/models.py | 4 | ||||
-rw-r--r-- | archaeological_files/models.py | 2 | ||||
-rw-r--r-- | archaeological_finds/models_finds.py | 9 | ||||
-rw-r--r-- | archaeological_operations/models.py | 14 | ||||
-rw-r--r-- | archaeological_warehouse/models.py | 2 | ||||
-rw-r--r-- | ishtar_common/models.py | 4 | ||||
-rw-r--r-- | ishtar_common/models_common.py | 2 | ||||
-rw-r--r-- | ishtar_common/models_imports.py | 1 | ||||
-rw-r--r-- | ishtar_common/utils.py | 7 |
9 files changed, 34 insertions, 11 deletions
diff --git a/archaeological_context_records/models.py b/archaeological_context_records/models.py index ccc145c48..e929e9957 100644 --- a/archaeological_context_records/models.py +++ b/archaeological_context_records/models.py @@ -1205,13 +1205,15 @@ class ContextRecord( def get_query_owns(cls, ishtaruser): return ( cls._construct_query_own( - "operation__", Operation._get_query_owns_dicts(ishtaruser) + cls, "operation__", Operation._get_query_owns_dicts(ishtaruser) ) | cls._construct_query_own( + cls, "base_finds__find__basket__", [{"shared_with": ishtaruser, "shared_write_with": ishtaruser}], ) | cls._construct_query_own( + cls, "", [ {"history_creator": ishtaruser.user_ptr}, diff --git a/archaeological_files/models.py b/archaeological_files/models.py index 06d927fcd..9e06db0f2 100644 --- a/archaeological_files/models.py +++ b/archaeological_files/models.py @@ -1360,7 +1360,7 @@ class File( @classmethod def get_query_owns(cls, ishtaruser): - return cls._construct_query_own("", cls._get_query_owns_dicts(ishtaruser)) + return cls._construct_query_own(cls, "", cls._get_query_owns_dicts(ishtaruser)) def is_active(self): return not bool(self.end_date) diff --git a/archaeological_finds/models_finds.py b/archaeological_finds/models_finds.py index 464076caf..78e1ec217 100644 --- a/archaeological_finds/models_finds.py +++ b/archaeological_finds/models_finds.py @@ -2972,20 +2972,25 @@ class Find( def _get_query_owns(cls, ishtaruser, prefix=""): q = ( cls._construct_query_own( - f"{prefix}container__location__", Warehouse._get_query_owns_dicts(ishtaruser) + cls, f"{prefix}container__location__", + Warehouse._get_query_owns_dicts(ishtaruser) ) | cls._construct_query_own( - f"{prefix}container__responsible__", Warehouse._get_query_owns_dicts(ishtaruser) + cls, f"{prefix}container__responsible__", + Warehouse._get_query_owns_dicts(ishtaruser) ) | cls._construct_query_own( + cls, f"{prefix}base_finds__context_record__operation__", Operation._get_query_owns_dicts(ishtaruser), ) | cls._construct_query_own( + cls, f"{prefix}basket__", [{"shared_with": ishtaruser, "shared_write_with": ishtaruser}], ) | cls._construct_query_own( + cls, "", [ {f"{prefix}history_creator": ishtaruser.user_ptr}, diff --git a/archaeological_operations/models.py b/archaeological_operations/models.py index 9119a5c72..42325d8be 100644 --- a/archaeological_operations/models.py +++ b/archaeological_operations/models.py @@ -856,32 +856,39 @@ class ArchaeologicalSite( q = ( cls._construct_query_own( + cls, "operations__context_record__base_finds__find__container__responsible__", Warehouse._get_query_owns_dicts(ishtaruser), ) | cls._construct_query_own( + cls, "operations__context_record__base_finds__find__basket__", [{"shared_with": ishtaruser, "shared_write_with": ishtaruser}], ) | cls._construct_query_own( + cls, "operations__context_record__base_finds__find__container__location__", Warehouse._get_query_owns_dicts(ishtaruser), ) | cls._construct_query_own( + cls, "top_operations__context_record__base_finds__find__container__responsible__", Warehouse._get_query_owns_dicts(ishtaruser), ) | cls._construct_query_own( + cls, "top_operations__context_record__base_finds__find__container__location__", Warehouse._get_query_owns_dicts(ishtaruser), ) | cls._construct_query_own( + cls, "operations__", Operation._get_query_owns_dicts(ishtaruser, no_rel=True) ) | cls._construct_query_own( + cls, "top_operations__", Operation._get_query_owns_dicts(ishtaruser) ) - | cls._construct_query_own("", cls._get_query_owns_dicts(ishtaruser)) + | cls._construct_query_own(cls, "", cls._get_query_owns_dicts(ishtaruser)) ) return q @@ -2294,18 +2301,21 @@ class Operation( q = ( cls._construct_query_own( + cls, "context_record__base_finds__find__container__responsible__", Warehouse._get_query_owns_dicts(ishtaruser), ) | cls._construct_query_own( + cls, "context_record__base_finds__find__container__location__", Warehouse._get_query_owns_dicts(ishtaruser), ) | cls._construct_query_own( + cls, "context_record__base_finds__find__basket__", [{"shared_with": ishtaruser, "shared_write_with": ishtaruser}], ) - | cls._construct_query_own("", cls._get_query_owns_dicts(ishtaruser)) + | cls._construct_query_own(cls, "", cls._get_query_owns_dicts(ishtaruser)) ) return q diff --git a/archaeological_warehouse/models.py b/archaeological_warehouse/models.py index 3cb04816d..db549912d 100644 --- a/archaeological_warehouse/models.py +++ b/archaeological_warehouse/models.py @@ -621,7 +621,7 @@ class Warehouse( @classmethod def get_query_owns(cls, ishtaruser): - return cls._construct_query_own("", cls._get_query_owns_dicts(ishtaruser)) + return cls._construct_query_own(cls, "", cls._get_query_owns_dicts(ishtaruser)) @classmethod def _get_query_owns_dicts(cls, ishtaruser): diff --git a/ishtar_common/models.py b/ishtar_common/models.py index abff81056..1ac95dd7e 100644 --- a/ishtar_common/models.py +++ b/ishtar_common/models.py @@ -5030,13 +5030,13 @@ class Document( query_own_list.append((rel_model + "__", q_own_dct)) q = None for prefix, owns in query_own_list: - subq = cls._construct_query_own(prefix, owns) + subq = cls._construct_query_own(cls, prefix, owns) if subq: if not q: q = subq else: q |= subq - q |= cls._construct_query_own("", [{"history_creator": ishtaruser.user_ptr}]) + q |= cls._construct_query_own(cls, "", [{"history_creator": ishtaruser.user_ptr}]) return q def get_associated_operation(self): diff --git a/ishtar_common/models_common.py b/ishtar_common/models_common.py index 6f995569c..91a3619ce 100644 --- a/ishtar_common/models_common.py +++ b/ishtar_common/models_common.py @@ -2427,7 +2427,7 @@ class GeoVectorData(Imported, OwnPerms): ): model = apps.get_model(app_label, model_name) sub_q = cls._construct_query_own( - "", model._get_query_owns_dicts(ishtaruser) + model, "", model._get_query_owns_dicts(ishtaruser) ) q2 = Q( source_id__in=list(sub_q.values_list("id", flat=True)), diff --git a/ishtar_common/models_imports.py b/ishtar_common/models_imports.py index 5e29b98ed..cae04298b 100644 --- a/ishtar_common/models_imports.py +++ b/ishtar_common/models_imports.py @@ -1483,6 +1483,7 @@ class BaseImport(models.Model, OwnPerms, SheetItem): @classmethod def get_query_owns(cls, ishtaruser): return cls._construct_query_own( + cls, "", [ {"importer_type__users__pk": ishtaruser.pk}, diff --git a/ishtar_common/utils.py b/ishtar_common/utils.py index e69ef0290..666e05bd9 100644 --- a/ishtar_common/utils.py +++ b/ishtar_common/utils.py @@ -530,12 +530,17 @@ class OwnPerms: return [] @classmethod - def _construct_query_own(cls, prefix, dct_list): + def _construct_query_own(cls, model, prefix, dct_list): q = None for subquery_dict in dct_list: subquery = None for k in subquery_dict: subsubquery = Q(**{prefix + k: subquery_dict[k]}) + # slice in multiple queries in order to prevent too complicated queries + subsubquery = Q(id__in=( + model.objects.filter(subsubquery).values_list("id", flat=True) + ) + ) if subquery: subquery |= subsubquery else: |