diff options
author | Étienne Loks <etienne.loks@iggdrasil.net> | 2020-12-04 16:12:23 +0100 |
---|---|---|
committer | Étienne Loks <etienne.loks@iggdrasil.net> | 2021-02-28 12:15:22 +0100 |
commit | 79fd79177cc6ab59315ed71fd0e2cb0f1fcd0f71 (patch) | |
tree | 9367c07079dc213b09d6dff6719fe3bb49aa3e67 | |
parent | df8486df514668440a8cc68448d95c1beafdb24a (diff) | |
download | Ishtar-79fd79177cc6ab59315ed71fd0e2cb0f1fcd0f71.tar.bz2 Ishtar-79fd79177cc6ab59315ed71fd0e2cb0f1fcd0f71.zip |
Add documents to administrative acts (refs #4999)
-rw-r--r-- | archaeological_files/migrations/0105_auto_20201204_1442.py | 25 | ||||
-rw-r--r-- | archaeological_operations/migrations/0106_auto_20201204_1557.py | 32 | ||||
-rw-r--r-- | archaeological_operations/models.py | 47 | ||||
-rw-r--r-- | archaeological_operations/templates/ishtar/sheet_administrativeact.html | 83 | ||||
-rw-r--r-- | archaeological_operations/urls.py | 3 | ||||
-rw-r--r-- | archaeological_operations/views.py | 33 | ||||
-rw-r--r-- | ishtar_common/models.py | 19 | ||||
-rw-r--r-- | ishtar_common/models_common.py | 7 | ||||
-rw-r--r-- | ishtar_common/templates/ishtar/sheet_document.html | 1 |
9 files changed, 193 insertions, 57 deletions
diff --git a/archaeological_files/migrations/0105_auto_20201204_1442.py b/archaeological_files/migrations/0105_auto_20201204_1442.py new file mode 100644 index 000000000..cb6b57143 --- /dev/null +++ b/archaeological_files/migrations/0105_auto_20201204_1442.py @@ -0,0 +1,25 @@ +# -*- coding: utf-8 -*- +# Generated by Django 1.11.27 on 2020-12-04 14:42 +from __future__ import unicode_literals + +from django.db import migrations, models + + +class Migration(migrations.Migration): + + dependencies = [ + ('archaeological_files', '0104_auto_20201203_1453'), + ] + + operations = [ + migrations.AddField( + model_name='file', + name='planning_service_date', + field=models.DateField(blank=True, null=True, verbose_name='Date of planning service file'), + ), + migrations.AddField( + model_name='historicalfile', + name='planning_service_date', + field=models.DateField(blank=True, null=True, verbose_name='Date of planning service file'), + ), + ] diff --git a/archaeological_operations/migrations/0106_auto_20201204_1557.py b/archaeological_operations/migrations/0106_auto_20201204_1557.py new file mode 100644 index 000000000..d93419443 --- /dev/null +++ b/archaeological_operations/migrations/0106_auto_20201204_1557.py @@ -0,0 +1,32 @@ +# -*- coding: utf-8 -*- +# Generated by Django 1.11.27 on 2020-12-04 15:57 +from __future__ import unicode_literals + +from django.db import migrations, models +import django.db.models.deletion + + +class Migration(migrations.Migration): + + dependencies = [ + ('ishtar_common', '0205_auto_20201203_1453'), + ('archaeological_operations', '0105_auto_20201203_1453'), + ] + + operations = [ + migrations.AddField( + model_name='administrativeact', + name='documents', + field=models.ManyToManyField(blank=True, related_name='administrativeacts', to='ishtar_common.Document', verbose_name='Documents'), + ), + migrations.AddField( + model_name='administrativeact', + name='main_image', + field=models.ForeignKey(blank=True, null=True, on_delete=django.db.models.deletion.SET_NULL, related_name='main_image_administrativeacts', to='ishtar_common.Document', verbose_name='Main image'), + ), + migrations.AddField( + model_name='historicaladministrativeact', + name='main_image', + field=models.ForeignKey(blank=True, db_constraint=False, null=True, on_delete=django.db.models.deletion.DO_NOTHING, related_name='+', to='ishtar_common.Document', verbose_name='Main image'), + ), + ] diff --git a/archaeological_operations/models.py b/archaeological_operations/models.py index 5ca822f73..f5bf540fa 100644 --- a/archaeological_operations/models.py +++ b/archaeological_operations/models.py @@ -598,11 +598,11 @@ class ArchaeologicalSite(DocumentItem, BaseHistorizedItem, CompleteIdentifierIte else: current_operations.pop(relation.right_record.pk) rel_type = RelationType.get_cache('has_got') - for missing in current_operations: + for missing, value in current_operations.items(): RecordRelations.objects.create( left_record=top_operation, - right_record=current_operations[missing], - relation_type=rel_type + right_record=value, + relation_type=rel_type, ) @@ -1708,12 +1708,11 @@ class Operation(ClosedItem, DocumentItem, BaseHistorizedItem, return self._get_or_set_stats('_nb_documents', update) def _nb_documents(self): - nbs = self.documents.count() + \ + return self.documents.count() + \ Document.objects.filter( context_records__operation=self).count() + \ Document.objects.filter( finds__base_finds__context_record__operation=self).count() - return nbs @property def nb_documents_by_types(self, update=False): @@ -1910,7 +1909,8 @@ post_save.connect(post_save_cache, sender=ActType) post_delete.connect(post_save_cache, sender=ActType) -class AdministrativeAct(BaseHistorizedItem, OwnPerms, ValueGetter): +class AdministrativeAct(DocumentItem, BaseHistorizedItem, OwnPerms, + ValueGetter): TABLE_COLS = ['full_ref', 'signature_date__year', 'index', 'act_type', 'act_object', 'signature_date', 'associated_file__cached_label', @@ -2190,6 +2190,13 @@ class AdministrativeAct(BaseHistorizedItem, OwnPerms, ValueGetter): towns_label = models.TextField( _("Towns"), blank=True, default="", help_text=_("Cached values get from associated towns")) + documents = models.ManyToManyField( + Document, related_name="administrativeacts", + verbose_name=_("Documents"), blank=True) + main_image = models.ForeignKey( + Document, related_name='main_image_administrativeacts', + on_delete=models.SET_NULL, + verbose_name=_("Main image"), blank=True, null=True) history = HistoricalRecords() _prefix = 'adminact_' @@ -2225,13 +2232,26 @@ class AdministrativeAct(BaseHistorizedItem, OwnPerms, ValueGetter): return 'delete-administrativeact-treatmentfile' def __str__(self): - return settings.JOINT.join( + lbl = "" + if self.year: + lbl = str(self.year) + if self.index: + lbl += "-{}".format(self.index) + if lbl: + lbl += " - " + lbl += self.act_type.label + " - " + return lbl + settings.JOINT.join( [str(item) for item in [ self.related_item, self.act_object] if item]) full_ref_lbl = _("Ref.") + def _get_base_image_path(self): + if self.year: + return str(self.year) + return "" + @property def full_ref(self): lbl = [] @@ -2294,14 +2314,11 @@ class AdministrativeAct(BaseHistorizedItem, OwnPerms, ValueGetter): return self.treatment_file def get_extra_templates(self, request): - templates = [] - for template in self.act_type.associated_template.all(): - urlname = "generatedoc-administrativeactop" - templates.append( - (template.name, reverse( - urlname, args=[self.pk, template.pk])) - ) - return templates + urlname = "generatedoc-administrativeactop" + return [ + (template.name, reverse(urlname, args=[self.pk, template.pk])) + for template in self.act_type.associated_template.all() + ] def get_filename(self): filename = self.related_item.associated_filename diff --git a/archaeological_operations/templates/ishtar/sheet_administrativeact.html b/archaeological_operations/templates/ishtar/sheet_administrativeact.html index f0026807c..843d5fc8d 100644 --- a/archaeological_operations/templates/ishtar/sheet_administrativeact.html +++ b/archaeological_operations/templates/ishtar/sheet_administrativeact.html @@ -1,5 +1,5 @@ {% extends "ishtar/sheet.html" %} -{% load i18n window_header window_field %} +{% load i18n window_header window_field window_tables link_to_window %} {% block head_title %}<strong>{% trans "Administrative act" %}</strong> - {{item.full_ref}}{% endblock %} @@ -20,37 +20,62 @@ {% block content %} -<h3>{% trans "General"%}</h3> -<div class="row"> - {% field_flex "Year" item.year %} - {% field_flex "Index" item.index %} - {% field_flex "Internal reference" item.ref_sra %} - {% field_flex "Type" item.act_type %} - {% field_flex "Object" item.act_object %} - {% field_flex_detail "Signatory" item.signatory %} - {% field_flex "Signature date" item.signature_date %} - {% field_flex "In charge" item.in_charge %} - {% field_flex "Archaeological preventive operator" item.operator %} - {% field_flex_detail "Associated file" item.associated_file %} - {% field_flex_detail "Operation" item.operation %} - {% field_flex_detail "Treatment" item.treatment %} - {% field_flex_detail "Treatment request" item.treatment_file %} - - {% if item.operation and item.operation.surface %} - <div class="col-12 col-md-6 col-lg-4 d-flex flex-wrap row"> - <dt class="col-5">{% trans "Surface"%}</dt> - <dd class='col-7'> - {{ item.operation.surface }} m<sup>2</sup> ({{ item.operation.surface_ha }} ha) - </dd> +{% with pdf_attached=item.pdf_attached %} +{% if pdf_attached %} +<p class="text-center col-12 p-2"> + <a href="{{pdf_attached}}" target="_blank"> + {% trans "View PDF" %} + <i class="fa fa-external-link" aria-hidden="true"></i> + </a> +</p> +{% endif %} +{% endwith %} + +<div class="clearfix"> + {% if item.images.count %} + <div class="card float-left col-12 col-md-6 col-lg-4"> + {% include "ishtar/blocks/window_image.html" %} </div> {% endif %} - {% field_flex_detail "Created by" item.history_creator.ishtaruser.person %} + <h3>{% trans "General"%}</h3> + <div class="row"> + {% field_flex "Year" item.year %} + {% field_flex "Index" item.index %} + {% field_flex "Internal reference" item.ref_sra %} + {% field_flex "Type" item.act_type %} + {% field_flex "Object" item.act_object %} + {% field_flex_detail "Signatory" item.signatory %} + {% field_flex "Signature date" item.signature_date %} + {% field_flex "In charge" item.in_charge %} + {% field_flex "Archaeological preventive operator" item.operator %} + {% field_flex_detail "Associated file" item.associated_file %} + {% field_flex_detail "Operation" item.operation %} + {% field_flex_detail "Treatment" item.treatment %} + {% field_flex_detail "Treatment request" item.treatment_file %} + + {% if item.operation and item.operation.surface %} + <div class="col-12 col-md-6 col-lg-4 d-flex flex-wrap row"> + <dt class="col-5">{% trans "Surface"%}</dt> + <dd class='col-7'> + {{ item.operation.surface }} m<sup>2</sup> ({{ item.operation.surface_ha }} ha) + </dd> + </div> + {% endif %} + {% field_flex_detail "Created by" item.history_creator.ishtaruser.person %} - {% comment %}{% if item.general_contractor.attached_to %}<p> - <label>{% trans "General contractor organisation"%}</label> - <span class='value'>{{ item.general_contractor.attached_to }}</span></p>{% endif %} <!-- Contractor's organisation displayed as concat of Name/Adress/postal_code/city --> - {% if item.general_contractor %}<p><label>{%trans "General contractor"%}</label> <span class='value'>{{ item.general_contractor.full_label }}</span></p>{% endif %} - {% endcomment %} + {% comment %}{% if item.general_contractor.attached_to %}<p> + <label>{% trans "General contractor organisation"%}</label> + <span class='value'>{{ item.general_contractor.attached_to }}</span></p>{% endif %} <!-- Contractor's organisation displayed as concat of Name/Adress/postal_code/city --> + {% if item.general_contractor %}<p><label>{%trans "General contractor"%}</label> <span class='value'>{{ item.general_contractor.full_label }}</span></p>{% endif %} + {% endcomment %} + </div> </div> + {% if item.documents.count %} + <div class="row spacer"> + <div class="col-12"> + {% dynamic_table_document 'Documents' 'documents' 'administrativeacts' item.pk '' output %} + </div> + </div> + {% endif %} {% endblock %} diff --git a/archaeological_operations/urls.py b/archaeological_operations/urls.py index 72e06641d..6961af39a 100644 --- a/archaeological_operations/urls.py +++ b/archaeological_operations/urls.py @@ -128,6 +128,9 @@ urlpatterns = [ name='generatedoc-administrativeactop'), url(r'dashboard_operation/$', views.dashboard_operation, name='dashboard-operation'), + url(r'autocomplete-administrativeact/$', + views.autocomplete_administrativeact, + name='autocomplete-administrativeact'), url(r'autocomplete-archaeologicalsite/$', views.autocomplete_archaeologicalsite, diff --git a/archaeological_operations/views.py b/archaeological_operations/views.py index 897302828..0c3dc28a1 100644 --- a/archaeological_operations/views.py +++ b/archaeological_operations/views.py @@ -84,7 +84,7 @@ def autocomplete_archaeologicalsite(request): query = query & qt limit = 15 sites = models.ArchaeologicalSite.objects.filter( - query).order_by('reference')[:limit] + query).distinct().order_by('reference')[:limit] data = json.dumps([{'id': site.pk, 'value': str(site)[:60]} for site in sites]) @@ -125,7 +125,7 @@ def autocomplete_operation(request): pass query = query & extra limit = 15 - operations = models.Operation.objects.filter(query)[:limit] + operations = models.Operation.objects.filter(query).distinct()[:limit] data = json.dumps([{'id': operation.pk, 'value': str(operation)} for operation in operations]) return HttpResponse(data, content_type='text/plain') @@ -566,6 +566,35 @@ def administrativeactfile_document( return render(request, 'ishtar/administrativeact_document.html', dct) +def autocomplete_administrativeact(request): + if (not request.user.has_perm( + 'archaeological_operations.view_administrativeact', + models.AdministrativeAct) + and not request.user.has_perm( + 'archaeological_operations.view_own_administrativeact', + models.AdministrativeAct)): + return HttpResponse(content_type='text/plain') + if not request.GET.get('term'): + return HttpResponse(content_type='text/plain') + q = request.GET.get('term') + query = Q() + for q in q.split(' '): + qt = Q(act_type__label__icontains=q) | Q(towns_label=q) + try: + if len(q) == 4: + qt |= Q(year=int(q)) + qt |= Q(index=int(q)) + except ValueError: + pass + query = query & qt + limit = 15 + items = models.AdministrativeAct.objects.filter( + query).order_by('year', 'index').distinct()[:limit] + data = json.dumps([{'id': item.pk, 'value': str(item)[:80] + " (...)"} + for item in items]) + return HttpResponse(data, content_type='text/plain') + + def reset_wizards(request): for wizard_class, url_name in ( (wizards.OperationWizard, 'operation_creation'), diff --git a/ishtar_common/models.py b/ishtar_common/models.py index ac3755e13..e841690bb 100644 --- a/ishtar_common/models.py +++ b/ishtar_common/models.py @@ -2714,19 +2714,21 @@ class Document(BaseHistorizedItem, CompleteIdentifierItem, OwnPerms, ImageModel, # other will be symbolic links RELATED_MODELS = [ 'treatment_files', 'treatments', 'finds', 'context_records', - 'operations', 'sites', 'warehouses', 'containers', 'files' + 'operations', 'sites', 'warehouses', 'containers', 'files', + 'administrativeacts', ] # same fields but in order for forms RELATED_MODELS_ALT = [ 'finds', 'context_records', 'operations', 'sites', 'files', - 'warehouses', 'containers', 'treatments', 'treatment_files', + 'administrativeacts', 'warehouses', 'containers', 'treatments', + 'treatment_files', ] SLUG = 'document' LINK_SPLIT = "<||>" GET_VALUES_EXCLUDE_FIELDS = ValueGetter.GET_VALUES_EXCLUDE_FIELDS + [ "warehouses", "operations", "treatments", - "files", "treatment_files", "id", + "files", "treatment_files", "administrativeacts", "id", "associated_links", "source_type_id", "history_creator_id", "containers", "sites", "main_image_warehouses", "main_image_operations", @@ -2977,6 +2979,7 @@ class Document(BaseHistorizedItem, CompleteIdentifierItem, OwnPerms, ImageModel, ('warehouse', 'warehouses__pk'), ('treatment', 'treatments__pk'), ('treatmentfile', 'treatment_files__pk'), + ('administrativeact', 'administrativeacts__pk'), ] UP_MODEL_QUERY = { @@ -3239,10 +3242,7 @@ class Document(BaseHistorizedItem, CompleteIdentifierItem, OwnPerms, ImageModel, def public_representation(self): site = Site.objects.get_current() - if settings.ISHTAR_SECURE: - scheme = "https" - else: - scheme = "http" + scheme = "https" if settings.ISHTAR_SECURE else "http" base_url = scheme + "://" + site.domain + "/" image = None if self.image: @@ -3334,10 +3334,7 @@ class Document(BaseHistorizedItem, CompleteIdentifierItem, OwnPerms, ImageModel, @property def has_related(self): - for rel in self.RELATED_MODELS: - if getattr(self, rel).count(): - return True - return False + return any(getattr(self, rel).count() for rel in self.RELATED_MODELS) @classmethod def get_query_owns(cls, ishtaruser): diff --git a/ishtar_common/models_common.py b/ishtar_common/models_common.py index 28026536a..17ba88419 100644 --- a/ishtar_common/models_common.py +++ b/ishtar_common/models_common.py @@ -2328,6 +2328,13 @@ class DocumentItem: image__isnull=False).exclude( image="").exclude(pk=self.main_image.pk).order_by("pk") + @property + def pdf_attached(self): + for document in self.documents.filter( + Q(associated_file__isnull=False) | + Q(source__associated_file__isnull=False)).all(): + return document.pdf_attached + def get_extra_actions(self, request): """ For sheet template: return "Add document / image" action diff --git a/ishtar_common/templates/ishtar/sheet_document.html b/ishtar_common/templates/ishtar/sheet_document.html index 08af1e928..5e74abe1c 100644 --- a/ishtar_common/templates/ishtar/sheet_document.html +++ b/ishtar_common/templates/ishtar/sheet_document.html @@ -118,6 +118,7 @@ {% if item.has_related %} <h3>{% trans "Related items" %}</h3> {% field_flex_full "Files" item.files|add_links %} +{% field_flex_full "Administrative acts" item.administrativeacts|add_links %} {% field_flex_full "Sites" item.sites|add_links %} {% field_flex_full "Operations" item.operations|add_links %} {% field_flex_full "Context records" item.context_records|add_links %} |