diff --git a/compensation/admin.py b/compensation/admin.py index c392195c..e77450a5 100644 --- a/compensation/admin.py +++ b/compensation/admin.py @@ -52,7 +52,7 @@ class EcoAccountWithdrawAdmin(admin.ModelAdmin): "id", "account", "intervention", - "amount", + "surface", ] diff --git a/compensation/filters.py b/compensation/filters.py index ab7a5fe7..f96cbb97 100644 --- a/compensation/filters.py +++ b/compensation/filters.py @@ -53,3 +53,48 @@ class CompensationTableFilter(InterventionTableFilter): ) else: return queryset + + +class EcoAccountTableFilter(InterventionTableFilter): + """ TableFilter for eco accounts + + Based widely on InterventionTableFilter. + Just some minor changes for EcoAccount model. + + """ + + def _filter_show_all(self, queryset, name, value) -> QuerySet: + """ Filters queryset depending on value of 'show_all' setting + + Args: + queryset (): + name (): + value (): + + Returns: + + """ + if not value: + return queryset.filter( + users__in=[self.user], # requesting user has access + ) + else: + return queryset + + def _filter_show_recorded(self, queryset, name, value) -> QuerySet: + """ Filters queryset depending on value of 'show_recorded' setting + + Args: + queryset (): + name (): + value (): + + Returns: + + """ + if not value: + return queryset.filter( + recorded=None, + ) + else: + return queryset diff --git a/compensation/models.py b/compensation/models.py index 35f2c717..ecd432af 100644 --- a/compensation/models.py +++ b/compensation/models.py @@ -175,6 +175,16 @@ class EcoAccount(AbstractCompensation): help_text="Users having access (shared with)" ) + # Refers to "verzeichnen" + recorded = models.OneToOneField( + UserActionLogEntry, + on_delete=models.SET_NULL, + null=True, + blank=True, + help_text="Holds data on user and timestamp of this action", + related_name="+" + ) + def __str__(self): return "{}".format(self.identifier) @@ -189,15 +199,14 @@ class EcoAccountWithdraw(BaseResource): null=True, blank=True, help_text="Withdrawn from", - related_name="eco_withdraws", + related_name="withdraws", ) - amount = models.FloatField( + surface = models.FloatField( null=True, blank=True, - help_text="Amount withdrawn (percentage)", + help_text="Amount withdrawn (m²)", validators=[ MinValueValidator(limit_value=0.00), - MaxValueValidator(limit_value=100), ] ) intervention = models.ForeignKey( @@ -206,8 +215,8 @@ class EcoAccountWithdraw(BaseResource): null=True, blank=True, help_text="Withdrawn for", - related_name="eco_withdraws", + related_name="withdraws", ) def __str__(self): - return "{} of {}".format(self.amount, self.account) + return "{} of {}".format(self.surface, self.account) diff --git a/compensation/tables.py b/compensation/tables.py index 6d0e7ca6..c8b5ae39 100644 --- a/compensation/tables.py +++ b/compensation/tables.py @@ -5,14 +5,16 @@ Contact: michel.peltriaux@sgdnord.rlp.de Created on: 01.12.20 """ +from django.db.models import Sum from django.http import HttpRequest +from django.template.loader import render_to_string from django.urls import reverse from django.utils.html import format_html from django.utils.timezone import localtime from django.utils.translation import gettext_lazy as _ -from compensation.filters import CompensationTableFilter -from compensation.models import Compensation +from compensation.filters import CompensationTableFilter, EcoAccountTableFilter +from compensation.models import Compensation, EcoAccount from intervention.filters import InterventionTableFilter from konova.sub_settings.django_settings import DEFAULT_DATE_TIME_FORMAT from konova.utils.tables import BaseTable @@ -57,7 +59,7 @@ class CompensationTable(BaseTable): class Meta(BaseTable.Meta): template_name = "django_tables2/bootstrap4.html" - def __init__(self, request:HttpRequest, *args, **kwargs): + def __init__(self, request: HttpRequest, *args, **kwargs): self.title = _("Compensations") self.add_new_url = reverse("compensation:new") qs = kwargs.get("queryset", None) @@ -170,43 +172,120 @@ class EcoAccountTable(BaseTable): orderable=True, accessor="title", ) - d = tables.Column( - verbose_name=_("Created on"), + av = tables.Column( + verbose_name=_("Available"), + orderable=True, + empty_values=[], + ) + r = tables.Column( + verbose_name=_("Recorded"), + orderable=True, + empty_values=[], + accessor="recorded", + ) + e = tables.Column( + verbose_name=_("Editable"), + orderable=True, + empty_values=[], + accessor="users", + ) + lm = tables.Column( + verbose_name=_("Last edit"), orderable=True, accessor="created__timestamp", ) - ac = tables.Column( - verbose_name=_("Actions"), - orderable=False, - empty_values=[], - attrs={"td": {"class": "action-col"}} - ) class Meta(BaseTable.Meta): - pass + template_name = "django_tables2/bootstrap4.html" - def __init__(self, *args, **kwargs): - super().__init__(*args, **kwargs) + def __init__(self, request: HttpRequest, *args, **kwargs): self.title = _("Eco Accounts") self.add_new_url = reverse("compensation:acc-new") + qs = kwargs.get("queryset", None) + self.filter = EcoAccountTableFilter( + user=request.user, + data=request.GET, + queryset=qs, + ) + super().__init__(request, self.filter, *args, **kwargs) + + def render_id(self, value, record: EcoAccount): + """ Renders the id column for an eco account + + Args: + value (str): The identifier value + record (EcoAccount): The eco account record + + Returns: - def render_ac(self, value, record): """ - Renders possible actions for this record, such as delete. - """ - intervention = _("Compensation") html = "" - html += self.render_open_btn( - _("Open {}").format(intervention), - reverse("compensation:open", args=(record.id,)), - new_tab=True - ) - html += self.render_edit_btn( - _("Edit {}").format(intervention), - reverse("compensation:edit", args=(record.id,)), - ) - html += self.render_delete_btn( - _("Delete {}").format(intervention), - reverse("compensation:remove", args=(record.id,)), + html += self.render_link( + tooltip=_("Open {}").format(_("Eco-account")), + href=reverse("compensation:acc-open", args=(record.id,)), + txt=value, + new_tab=False, + ) + return format_html(html) + + def render_av(self, value, record: EcoAccount): + """ Renders the available column for an eco account + + Args: + value (str): The identifier value + record (EcoAccount): The eco account record + + Returns: + + """ + withdraws = record.withdraws.all() + withdraw_surfaces = withdraws.aggregate(Sum("amount"))["amount__sum"] or 0 + after_states_surfaces = record.after_states.all().aggregate(Sum("surface"))["surface__sum"] or withdraw_surfaces ## no division by zero + value = int(((after_states_surfaces - withdraw_surfaces) / after_states_surfaces) * 100) + html = render_to_string("konova/custom_widgets/progressbar.html", {"value": value}) + return format_html(html) + + def render_r(self, value, record: EcoAccount): + """ Renders the registered column for an eco account + + Args: + value (str): The identifier value + record (EcoAccount): The eco account record + + Returns: + + """ + html = "" + checked = value is not None + tooltip = _("Not recorded yet. Can not be used for withdraws, yet.") + if checked: + value = value.timestamp + value = localtime(value) + on = value.strftime(DEFAULT_DATE_TIME_FORMAT) + tooltip = _("Recorded on {} by {}").format(on, record.recorded.user) + html += self.render_bookmark( + tooltip=tooltip, + icn_filled=checked, + ) + return format_html(html) + + def render_e(self, value, record: EcoAccount): + """ Renders the registered column for an eco account + + Args: + value (str): The identifier value + record (EcoAccount): The eco account record + + Returns: + + """ + html = "" + has_access = value.filter( + username=self.user.username + ).exists() + + html += self.render_icn( + tooltip=_("Full access granted") if has_access else _("Access not granted"), + icn_class="fas fa-edit rlp-r-inv" if has_access else "far fa-edit", ) return format_html(html) diff --git a/compensation/views/eco_account_views.py b/compensation/views/eco_account_views.py index 3c63b867..67c407f4 100644 --- a/compensation/views/eco_account_views.py +++ b/compensation/views/eco_account_views.py @@ -90,7 +90,7 @@ def withdraw_remove_view(request: HttpRequest, id: str, withdraw_id: str): """ acc = get_object_or_404(EcoAccount, id=id) try: - eco_withdraw = acc.eco_withdraws.get(id=withdraw_id) + eco_withdraw = acc.withdraws.get(id=withdraw_id) except ObjectDoesNotExist: raise Http404("Unknown withdraw") diff --git a/intervention/templates/intervention/detail/includes/eco-account-withdraws.html b/intervention/templates/intervention/detail/includes/eco-account-withdraws.html index 0aad1d8c..84a1bca5 100644 --- a/intervention/templates/intervention/detail/includes/eco-account-withdraws.html +++ b/intervention/templates/intervention/detail/includes/eco-account-withdraws.html @@ -4,7 +4,7 @@
- {{intervention.eco_withdraws.count}} + {{intervention.withdraws.count}} {% trans 'Eco Account Withdraws' %}
@@ -38,7 +38,7 @@ - {% for withdraw in intervention.eco_withdraws.all %} + {% for withdraw in intervention.withdraws.all %} diff --git a/konova/templates/konova/custom_widgets/progressbar.html b/konova/templates/konova/custom_widgets/progressbar.html new file mode 100644 index 00000000..abf6afd3 --- /dev/null +++ b/konova/templates/konova/custom_widgets/progressbar.html @@ -0,0 +1,7 @@ +{% load i18n %} + +
+
+ {{ value }} % +
+
\ No newline at end of file diff --git a/locale/de/LC_MESSAGES/django.mo b/locale/de/LC_MESSAGES/django.mo index fcc2b162..acd9eb4a 100644 Binary files a/locale/de/LC_MESSAGES/django.mo and b/locale/de/LC_MESSAGES/django.mo differ diff --git a/locale/de/LC_MESSAGES/django.po b/locale/de/LC_MESSAGES/django.po index d4953186..c375599e 100644 --- a/locale/de/LC_MESSAGES/django.po +++ b/locale/de/LC_MESSAGES/django.po @@ -8,15 +8,15 @@ #: intervention/filters.py:26 intervention/filters.py:40 #: intervention/filters.py:47 intervention/filters.py:48 #: intervention/forms.py:318 intervention/forms.py:330 -#: intervention/forms.py:342 konova/forms.py:92 konova/forms.py:228 -#: konova/forms.py:261 konova/forms.py:266 konova/forms.py:278 -#: konova/forms.py:290 konova/forms.py:303 user/forms.py:38 +#: intervention/forms.py:342 konova/forms.py:91 konova/forms.py:227 +#: konova/forms.py:260 konova/forms.py:265 konova/forms.py:277 +#: konova/forms.py:289 konova/forms.py:302 user/forms.py:38 #, fuzzy msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2021-08-05 12:43+0200\n" +"POT-Creation-Date: 2021-08-09 14:12+0200\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "Last-Translator: FULL NAME \n" "Language-Team: LANGUAGE \n" @@ -94,7 +94,7 @@ msgstr "Geben Sie die Daten des neuen Zustandes ein" msgid "Added state" msgstr "Zustand hinzugefügt" -#: compensation/forms.py:133 konova/forms.py:142 +#: compensation/forms.py:133 konova/forms.py:141 msgid "Object removed" msgstr "Objekt entfernt" @@ -123,12 +123,12 @@ msgstr "Datum wählen" #: intervention/forms.py:341 #: intervention/templates/intervention/detail/includes/documents.html:31 #: intervention/templates/intervention/detail/includes/revocation.html:35 -#: konova/forms.py:289 +#: konova/forms.py:288 msgid "Comment" msgstr "Kommentar" #: compensation/forms.py:204 compensation/forms.py:272 -#: intervention/forms.py:343 konova/forms.py:291 +#: intervention/forms.py:343 konova/forms.py:290 msgid "Additional comment, maximum {} letters" msgstr "Zusätzlicher Kommentar, maximal {} Zeichen" @@ -200,106 +200,109 @@ msgstr "" msgid "Pieces" msgstr "Stück" -#: compensation/tables.py:24 compensation/tables.py:164 +#: compensation/tables.py:26 compensation/tables.py:166 #: intervention/forms.py:28 intervention/tables.py:23 #: intervention/templates/intervention/detail/includes/compensations.html:30 msgid "Identifier" msgstr "Kennung" -#: compensation/tables.py:29 compensation/tables.py:169 +#: compensation/tables.py:31 compensation/tables.py:171 #: compensation/templates/compensation/detail/includes/documents.html:28 #: compensation/templates/compensation/detail/view.html:24 #: intervention/forms.py:35 intervention/tables.py:28 #: intervention/templates/intervention/detail/includes/compensations.html:33 #: intervention/templates/intervention/detail/includes/documents.html:28 -#: intervention/templates/intervention/detail/view.html:24 konova/forms.py:260 +#: intervention/templates/intervention/detail/view.html:24 konova/forms.py:259 msgid "Title" msgstr "Bezeichnung" -#: compensation/tables.py:34 +#: compensation/tables.py:36 #: compensation/templates/compensation/detail/view.html:36 #: intervention/tables.py:33 #: intervention/templates/intervention/detail/view.html:56 user/models.py:48 msgid "Checked" msgstr "Geprüft" -#: compensation/tables.py:40 +#: compensation/tables.py:42 compensation/tables.py:181 #: compensation/templates/compensation/detail/view.html:50 #: intervention/tables.py:39 #: intervention/templates/intervention/detail/view.html:70 user/models.py:49 msgid "Recorded" msgstr "Verzeichnet" -#: compensation/tables.py:46 intervention/tables.py:45 +#: compensation/tables.py:48 compensation/tables.py:187 +#: intervention/tables.py:45 msgid "Editable" msgstr "Freigegeben" -#: compensation/tables.py:52 intervention/tables.py:51 +#: compensation/tables.py:54 compensation/tables.py:193 +#: intervention/tables.py:51 msgid "Last edit" msgstr "Zuletzt bearbeitet" -#: compensation/tables.py:61 +#: compensation/tables.py:63 #: intervention/templates/intervention/detail/includes/compensations.html:8 msgid "Compensations" msgstr "Kompensationen" -#: compensation/tables.py:83 compensation/tables.py:200 +#: compensation/tables.py:85 compensation/tables.py:224 #: intervention/tables.py:92 intervention/tables.py:175 msgid "Open {}" msgstr "Öffne {}" -#: compensation/tables.py:83 compensation/tables.py:197 +#: compensation/tables.py:85 #: compensation/templates/compensation/detail/view.html:12 #: konova/templates/konova/home.html:49 templates/navbar.html:28 msgid "Compensation" msgstr "Kompensation" -#: compensation/tables.py:104 intervention/tables.py:111 +#: compensation/tables.py:106 intervention/tables.py:111 msgid "Not checked yet" msgstr "Noch nicht geprüft" -#: compensation/tables.py:109 intervention/tables.py:116 +#: compensation/tables.py:111 intervention/tables.py:116 msgid "Checked on {} by {}" msgstr "Am {} von {} geprüft worden" -#: compensation/tables.py:128 +#: compensation/tables.py:130 #: compensation/templates/compensation/detail/view.html:53 #: intervention/tables.py:135 #: intervention/templates/intervention/detail/view.html:73 msgid "Not recorded yet" msgstr "Noch nicht verzeichnet" -#: compensation/tables.py:133 intervention/tables.py:140 +#: compensation/tables.py:135 compensation/tables.py:265 +#: intervention/tables.py:140 msgid "Recorded on {} by {}" msgstr "Am {} von {} verzeichnet worden" -#: compensation/tables.py:156 intervention/tables.py:163 +#: compensation/tables.py:158 compensation/tables.py:288 +#: intervention/tables.py:163 msgid "Full access granted" msgstr "Für Sie freigegeben - Datensatz kann bearbeitet werden" -#: compensation/tables.py:156 intervention/tables.py:163 +#: compensation/tables.py:158 compensation/tables.py:288 +#: intervention/tables.py:163 msgid "Access not granted" msgstr "Nicht freigegeben - Datensatz nur lesbar" -#: compensation/tables.py:174 konova/forms.py:265 -msgid "Created on" -msgstr "Erstellt" +#: compensation/tables.py:176 +msgid "Available" +msgstr "Verfügbar" -#: compensation/tables.py:179 -msgid "Actions" -msgstr "Aktionen" - -#: compensation/tables.py:190 +#: compensation/tables.py:202 msgid "Eco Accounts" msgstr "Ökokonten" -#: compensation/tables.py:205 intervention/tables.py:179 -msgid "Edit {}" -msgstr "Bearbeite {}" +#: compensation/tables.py:224 konova/templates/konova/home.html:88 +#: templates/navbar.html:34 +msgid "Eco-account" +msgstr "Ökokonto" -#: compensation/tables.py:209 intervention/tables.py:183 -msgid "Delete {}" -msgstr "Lösche {}" +#: compensation/tables.py:260 +msgid "Not recorded yet. Can not be used for withdraws, yet." +msgstr "" +"Noch nicht verzeichnet. Kann noch nicht für Abbuchungen genutzt werden." #: compensation/templates/compensation/detail/includes/actions.html:8 msgctxt "Compensation" @@ -353,11 +356,12 @@ msgid "Edit" msgstr "Bearbeiten" #: compensation/templates/compensation/detail/includes/controls.html:21 +#: intervention/templates/intervention/detail/includes/controls.html:36 msgid "Show log" msgstr "Log anzeigen" #: compensation/templates/compensation/detail/includes/controls.html:24 -#: intervention/templates/intervention/detail/includes/controls.html:36 +#: intervention/templates/intervention/detail/includes/controls.html:39 #: venv/lib/python3.7/site-packages/django/forms/formsets.py:391 msgid "Delete" msgstr "Löschen" @@ -386,7 +390,7 @@ msgstr "Dokumente" #: compensation/templates/compensation/detail/includes/documents.html:14 #: intervention/templates/intervention/detail/includes/documents.html:14 -#: konova/forms.py:302 +#: konova/forms.py:301 msgid "Add new document" msgstr "Neues Dokument hinzufügen" @@ -466,50 +470,50 @@ msgstr "Freigegeben für" msgid "No geometry added, yet." msgstr "Keine Geometrie vorhanden" -#: compensation/views.py:127 +#: compensation/views/compensation_views.py:121 intervention/views.py:391 msgid "Log" msgstr "Log" -#: compensation/views.py:148 +#: compensation/views/compensation_views.py:142 msgid "Compensation removed" msgstr "Kompensation entfernt" -#: compensation/views.py:228 -msgid "Payment added" -msgstr "Zahlung hinzugefügt" - -#: compensation/views.py:263 -msgid "Payment removed" -msgstr "Zahlung gelöscht" - -#: compensation/views.py:289 -msgid "Withdraw removed" -msgstr "Abbuchung entfernt" - -#: compensation/views.py:307 intervention/views.py:96 +#: compensation/views/compensation_views.py:159 intervention/views.py:96 msgid "Document added" msgstr "Dokument hinzugefügt" -#: compensation/views.py:326 +#: compensation/views/compensation_views.py:178 msgid "State added" msgstr "Zustand hinzugefügt" -#: compensation/views.py:345 +#: compensation/views/compensation_views.py:197 msgid "Action added" msgstr "Maßnahme hinzugefügt" -#: compensation/views.py:364 +#: compensation/views/compensation_views.py:216 msgid "Deadline added" msgstr "Frist hinzugefügt" -#: compensation/views.py:383 +#: compensation/views/compensation_views.py:235 msgid "State removed" msgstr "Zustand gelöscht" -#: compensation/views.py:402 +#: compensation/views/compensation_views.py:254 msgid "Action removed" msgstr "Maßnahme entfernt" +#: compensation/views/eco_account_views.py:100 +msgid "Withdraw removed" +msgstr "Abbuchung entfernt" + +#: compensation/views/payment_views.py:43 +msgid "Payment added" +msgstr "Zahlung hinzugefügt" + +#: compensation/views/payment_views.py:78 +msgid "Payment removed" +msgstr "Zahlung gelöscht" + #: intervention/filters.py:25 msgid "Show unshared" msgstr "Nicht freigegebene anzeigen" @@ -622,7 +626,7 @@ msgstr "Datum des Widerspruchs" msgid "Document" msgstr "Dokument" -#: intervention/forms.py:331 konova/forms.py:279 +#: intervention/forms.py:331 konova/forms.py:278 msgid "Must be smaller than 15 Mb" msgstr "Muss kleiner als 15 Mb sein" @@ -653,6 +657,14 @@ msgstr "" "wurden:" #: intervention/models.py:216 +#: intervention/templates/intervention/detail/view.html:23 +#: intervention/templates/intervention/detail/view.html:27 +#: intervention/templates/intervention/detail/view.html:31 +#: intervention/templates/intervention/detail/view.html:39 +#: intervention/templates/intervention/detail/view.html:51 +#: intervention/templates/intervention/detail/view.html:83 +#: intervention/templates/intervention/detail/view.html:87 +#: intervention/templates/intervention/detail/view.html:91 msgid "Missing" msgstr "Fehlt" @@ -670,6 +682,14 @@ msgstr "Eingriffe" msgid "Intervention" msgstr "Eingriff" +#: intervention/tables.py:179 +msgid "Edit {}" +msgstr "Bearbeite {}" + +#: intervention/tables.py:183 +msgid "Delete {}" +msgstr "Lösche {}" + #: intervention/templates/intervention/detail/includes/compensations.html:14 msgid "Add new compensation" msgstr "Neue Kompensation hinzufügen" @@ -848,36 +868,40 @@ msgstr "" msgid "You need to be part of another user group." msgstr "Hierfür müssen Sie einer anderen Nutzergruppe angehören!" -#: konova/forms.py:65 +#: konova/forms.py:64 msgid "Not editable" msgstr "Nicht editierbar" -#: konova/forms.py:91 konova/forms.py:227 +#: konova/forms.py:90 konova/forms.py:226 msgid "Confirm" msgstr "Bestätige" -#: konova/forms.py:103 konova/forms.py:236 +#: konova/forms.py:102 konova/forms.py:235 msgid "Remove" msgstr "Löschen" -#: konova/forms.py:105 +#: konova/forms.py:104 msgid "You are about to remove {} {}" msgstr "Sie sind dabei {} {} zu löschen" -#: konova/forms.py:237 +#: konova/forms.py:236 msgid "Are you sure?" msgstr "Sind Sie sicher?" -#: konova/forms.py:267 +#: konova/forms.py:264 +msgid "Created on" +msgstr "Erstellt" + +#: konova/forms.py:266 msgid "When has this file been created? Important for photos." msgstr "Wann wurde diese Datei erstellt oder das Foto aufgenommen?" -#: konova/forms.py:277 +#: konova/forms.py:276 #: venv/lib/python3.7/site-packages/django/db/models/fields/files.py:231 msgid "File" msgstr "Datei" -#: konova/forms.py:327 +#: konova/forms.py:326 msgid "Added document" msgstr "Dokument hinzugefügt" @@ -921,6 +945,10 @@ msgstr "Kontrolle am" msgid "Other" msgstr "Sonstige" +#: konova/templates/konova/custom_widgets/progressbar.html:3 +msgid "Available: " +msgstr "" + #: konova/templates/konova/custom_widgets/text-to-clipboard-input.html:6 msgid "Copy to clipboard" msgstr "In Zwischenablage kopieren" @@ -949,10 +977,6 @@ msgstr "Neu" msgid "Show" msgstr "Anzeigen" -#: konova/templates/konova/home.html:88 templates/navbar.html:34 -msgid "Eco-account" -msgstr "Ökokonto" - #: konova/templates/konova/home.html:130 msgid "Withdraw" msgstr "Abbuchen" @@ -2377,6 +2401,9 @@ msgstr "" msgid "A fontawesome icon field" msgstr "" +#~ msgid "Actions" +#~ msgstr "Aktionen" + #~ msgid "Additional comment" #~ msgstr "Zusätzlicher Kommentar"