summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorÉtienne Loks <etienne.loks@iggdrasil.net>2023-12-18 18:56:31 +0100
committerÉtienne Loks <etienne.loks@iggdrasil.net>2024-04-16 16:38:33 +0200
commit56c5f6e31f34e47d9a6c31767840c9d949d63abf (patch)
treec293968531fba747a39d464ac6b571dc39d99b2e
parentef878c317f8aa33b5fdd92417a12e1385454e86e (diff)
downloadIshtar-56c5f6e31f34e47d9a6c31767840c9d949d63abf.tar.bz2
Ishtar-56c5f6e31f34e47d9a6c31767840c9d949d63abf.zip
✨ imports: add search criteria
-rw-r--r--archaeological_context_records/models.py3
-rw-r--r--archaeological_files/models.py2
-rw-r--r--archaeological_finds/models_finds.py2
-rw-r--r--archaeological_operations/models.py3
-rw-r--r--archaeological_warehouse/models.py3
-rw-r--r--changelog/en/changelog_2022-06-15.md1
-rw-r--r--changelog/fr/changelog_2023-01-25.md1
-rw-r--r--ishtar_common/forms.py25
-rw-r--r--ishtar_common/models.py2
-rw-r--r--ishtar_common/models_common.py27
-rw-r--r--ishtar_common/urls.py1
-rw-r--r--ishtar_common/views.py27
-rw-r--r--ishtar_common/views_item.py2
13 files changed, 84 insertions, 15 deletions
diff --git a/archaeological_context_records/models.py b/archaeological_context_records/models.py
index 9ad6da489..4940a2d4a 100644
--- a/archaeological_context_records/models.py
+++ b/archaeological_context_records/models.py
@@ -45,7 +45,7 @@ from ishtar_common.models import (
GeneralType,
BaseHistorizedItem,
OwnPerms,
- ShortMenuItem,
+ Imported,
GeneralRelationType,
GeneralRecordRelations,
post_delete_record_relation,
@@ -621,6 +621,7 @@ class ContextRecord(
ALT_NAMES.update(DocumentItem.ALT_NAMES)
ALT_NAMES.update(Dating.ASSOCIATED_ALT_NAMES)
ALT_NAMES.update(GeoItem.ALT_NAMES)
+ ALT_NAMES.update(Imported.ALT_NAMES)
PARENT_ONLY_SEARCH_VECTORS = ["operation", "archaeological_site", "parcel"]
BASE_SEARCH_VECTORS = [
diff --git a/archaeological_files/models.py b/archaeological_files/models.py
index 956f91421..1f2298b32 100644
--- a/archaeological_files/models.py
+++ b/archaeological_files/models.py
@@ -42,6 +42,7 @@ from ishtar_common.models import (
Department,
GeneralType,
BaseHistorizedItem,
+ Imported,
OwnPerms,
Person,
Organization,
@@ -520,6 +521,7 @@ class File(
}
ALT_NAMES.update(BaseHistorizedItem.ALT_NAMES)
ALT_NAMES.update(DocumentItem.ALT_NAMES)
+ ALT_NAMES.update(Imported.ALT_NAMES)
POST_PROCESS_REQUEST = {
"towns__numero_insee__startswith": "_get_department_code",
diff --git a/archaeological_finds/models_finds.py b/archaeological_finds/models_finds.py
index 9e576d16d..cb431f7cc 100644
--- a/archaeological_finds/models_finds.py
+++ b/archaeological_finds/models_finds.py
@@ -49,6 +49,7 @@ from ishtar_common.models import (
BaseHistorizedItem,
LightHistorizedItem,
OwnPerms,
+ Imported,
Person,
Basket,
post_save_cache,
@@ -1518,6 +1519,7 @@ class Find(
ALT_NAMES.update(DocumentItem.ALT_NAMES)
ALT_NAMES.update(Dating.ASSOCIATED_ALT_NAMES)
ALT_NAMES.update(GeoItem.ALT_NAMES_FOR_FIND())
+ ALT_NAMES.update(Imported.ALT_NAMES)
"""
# kept as an example
diff --git a/archaeological_operations/models.py b/archaeological_operations/models.py
index 3ebf98349..cec9b0869 100644
--- a/archaeological_operations/models.py
+++ b/archaeological_operations/models.py
@@ -49,6 +49,7 @@ from ishtar_common.models import (
GeneralRelationType,
GeneralType,
GeoVectorData,
+ Imported,
IshtarUser,
LightHistorizedItem,
OperationType,
@@ -434,6 +435,7 @@ class ArchaeologicalSite(
ALT_NAMES.update(BaseHistorizedItem.ALT_NAMES)
ALT_NAMES.update(DocumentItem.ALT_NAMES)
ALT_NAMES.update(GeoItem.ALT_NAMES)
+ ALT_NAMES.update(Imported.ALT_NAMES)
UP_MODEL_QUERY = {
"operation": (
@@ -1256,6 +1258,7 @@ class Operation(
ALT_NAMES.update(BaseHistorizedItem.ALT_NAMES)
ALT_NAMES.update(DocumentItem.ALT_NAMES)
ALT_NAMES.update(GeoItem.ALT_NAMES)
+ ALT_NAMES.update(Imported.ALT_NAMES)
QA_EDIT = QuickAction(
url="operation-qa-bulk-update",
diff --git a/archaeological_warehouse/models.py b/archaeological_warehouse/models.py
index 08d3e7d8d..e04643c87 100644
--- a/archaeological_warehouse/models.py
+++ b/archaeological_warehouse/models.py
@@ -35,7 +35,7 @@ from ishtar_common.utils import ugettext_lazy as _, pgettext_lazy
from django.apps import apps
from ishtar_common.data_importer import post_importer_action, pre_importer_action, ImporterError
from ishtar_common.model_managers import ExternalIdManager, UUIDModelManager
-from ishtar_common.models import ValueGetter, get_current_profile, HistoryModel
+from ishtar_common.models import ValueGetter, get_current_profile, HistoryModel, Imported
from ishtar_common.models_common import (
GeneralType,
BaseHistorizedItem,
@@ -1070,6 +1070,7 @@ class Container(
ALT_NAMES.update(BaseHistorizedItem.ALT_NAMES)
ALT_NAMES.update(DocumentItem.ALT_NAMES)
+ ALT_NAMES.update(Imported.ALT_NAMES)
"""
# kept as an example
diff --git a/changelog/en/changelog_2022-06-15.md b/changelog/en/changelog_2022-06-15.md
index 80ea86498..b86900454 100644
--- a/changelog/en/changelog_2022-06-15.md
+++ b/changelog/en/changelog_2022-06-15.md
@@ -16,6 +16,7 @@ v4.0.XX - 2099-12-31
- improved presentation
- imports - sheet (links from other sheet to the import sheet)
- imports - match: do not propose "Set to NULL" for required columns
+- searches: add criteria "imported from"
### Technical ###
- update relationship between imports and main items
diff --git a/changelog/fr/changelog_2023-01-25.md b/changelog/fr/changelog_2023-01-25.md
index bde37eb04..35a1bfb82 100644
--- a/changelog/fr/changelog_2023-01-25.md
+++ b/changelog/fr/changelog_2023-01-25.md
@@ -16,6 +16,7 @@ v4.0.XX - 2099-12-31
- amélioration de la présentation
- imports - fiche (liens des autres fiches vers la fiche import)
- imports - correspondance : ne pas proposer « Mettre à NULL » quand le champ est obligatoire
+- recherche : ajout du critère « importé depuis »
### Technique ###
- relation de mise à jour entre imports et les éléments principaux
diff --git a/ishtar_common/forms.py b/ishtar_common/forms.py
index c560dc5ec..b81b42bc6 100644
--- a/ishtar_common/forms.py
+++ b/ishtar_common/forms.py
@@ -1000,7 +1000,28 @@ class HistorySelect(CustomForm, TableSelect):
self.custom_form_ordering()
-class DocumentItemSelect(HistorySelect):
+class ImportSelect(HistorySelect):
+ imports = forms.IntegerField(
+ label=_("Imported from"),
+ widget=widgets.JQueryAutoComplete(
+ reverse_lazy(
+ 'autocomplete-import',
+ ),
+ associated_model=models.Import),
+ validators=[models.valid_id(models.Import)])
+ CURRENT_FIELDS = [
+ "imports",
+ ] + HistorySelect.CURRENT_FIELDS
+ _explicit_ordering = True
+
+ def __init__(self, *args, **kwargs):
+ user = kwargs.get("user", None)
+ super().__init__(*args, **kwargs)
+ if not user or (not user.has_perm("view_import") and not user.has_perm("view_own_import")):
+ self.fields.pop("imports")
+
+
+class DocumentItemSelect(ImportSelect):
documents__image__isnull = forms.NullBooleanField(label=_("Has an image?"))
documents__associated_file__isnull = forms.NullBooleanField(
label=_("Has an attached file?")
@@ -1012,7 +1033,7 @@ class DocumentItemSelect(HistorySelect):
"documents__image__isnull",
"documents__associated_file__isnull",
"documents__associated_url__isnull",
- ] + HistorySelect.CURRENT_FIELDS
+ ] + ImportSelect.CURRENT_FIELDS
_explicit_ordering = True
diff --git a/ishtar_common/models.py b/ishtar_common/models.py
index d7a546696..696020c58 100644
--- a/ishtar_common/models.py
+++ b/ishtar_common/models.py
@@ -147,6 +147,7 @@ from ishtar_common.models_common import (
SearchAltName,
OwnPerms,
Cached,
+ Imported,
Address,
post_save_cache,
TemplateItem,
@@ -188,6 +189,7 @@ __all__ = [
"ImporterDefaultValues",
"ImporterColumn",
"ImporterDuplicateField",
+ "Imported",
"Regexp",
"ImportTarget",
"ItemKey",
diff --git a/ishtar_common/models_common.py b/ishtar_common/models_common.py
index 658c7d157..c8686d7b3 100644
--- a/ishtar_common/models_common.py
+++ b/ishtar_common/models_common.py
@@ -1094,6 +1094,16 @@ class FullSearch(models.Model):
return changed
+class SearchAltName(object):
+ def __init__(
+ self, search_key, search_query, extra_query=None, distinct_query=False
+ ):
+ self.search_key = search_key
+ self.search_query = search_query
+ self.extra_query = extra_query or {}
+ self.distinct_query = distinct_query
+
+
class Imported(models.Model):
imports = models.ManyToManyField(
Import, blank=True, related_name="imported_%(app_label)s_%(class)s"
@@ -1104,6 +1114,13 @@ class Imported(models.Model):
Import, blank=True, related_name="import_updated_%(app_label)s_%(class)s"
)
+ ALT_NAMES = {
+ "imports": SearchAltName(
+ pgettext_lazy("key for text search", "imports"),
+ "imports__name__iexact",
+ ),
+ }
+
class Meta:
abstract = True
@@ -1303,16 +1320,6 @@ class FixAssociated:
setattr(item, subkey, new_value)
-class SearchAltName(object):
- def __init__(
- self, search_key, search_query, extra_query=None, distinct_query=False
- ):
- self.search_key = search_key
- self.search_query = search_query
- self.extra_query = extra_query or {}
- self.distinct_query = distinct_query
-
-
class HistoryError(Exception):
def __init__(self, value):
self.value = value
diff --git a/ishtar_common/urls.py b/ishtar_common/urls.py
index c3d614ac6..85d56aeb7 100644
--- a/ishtar_common/urls.py
+++ b/ishtar_common/urls.py
@@ -464,6 +464,7 @@ urlpatterns += [
views.show_import,
name="show-import",
),
+ url(r"autocomplete-import/$", views.autocomplete_import, name="autocomplete-import"),
url(
r"show-importgroup(?:/(?P<pk>\d+))?/(?P<type>odt|pdf)?$",
views.show_import_group,
diff --git a/ishtar_common/views.py b/ishtar_common/views.py
index 55a5947c0..3d86583b1 100644
--- a/ishtar_common/views.py
+++ b/ishtar_common/views.py
@@ -886,6 +886,33 @@ def autocomplete_person(
return HttpResponse(data, content_type="text/plain")
+def autocomplete_import(request):
+ all_items = request.user.has_perm("ishtar_common.view_import", models.Import)
+ own_items = False
+ if not all_items:
+ own_items = request.user.has_perm(
+ "ishtar_common.view_own_import", models.Import
+ )
+ if not all_items and not own_items or not request.GET.get("term"):
+ return HttpResponse("[]", content_type="text/plain")
+ q = request.GET.get("term")
+ limit = request.GET.get("limit", 20)
+ try:
+ limit = int(limit)
+ except ValueError:
+ return HttpResponseBadRequest()
+ query = Q()
+ for q in q.split(" "):
+ query = query & (Q(name__unaccent__icontains=q) | Q(group__name__unaccent__icontains=q))
+ if own_items:
+ if not hasattr(request.user, "ishtaruser"):
+ return HttpResponse(json.dumps([]), content_type="text/plain")
+ query &= models.Import.get_query_owns(request.user.ishtaruser)
+ items = models.Import.objects.filter(query).distinct()[:limit]
+ data = [{"id": item.pk, "value": item.name} for item in items if item]
+ return HttpResponse(json.dumps(data), content_type="text/plain")
+
+
def autocomplete_area(request):
if not request.GET.get("term"):
return HttpResponse("[]", content_type="text/plain")
diff --git a/ishtar_common/views_item.py b/ishtar_common/views_item.py
index d71775921..846646d6b 100644
--- a/ishtar_common/views_item.py
+++ b/ishtar_common/views_item.py
@@ -2237,7 +2237,7 @@ def get_item(
items_nb = 0
if count:
return items_nb
- # print(str(items.values("id").query).encode('utf-8'))
+ # print(str(items.values("id").query))
if search_vector: # for serialization
dct["search_vector"] = search_vector