Phase 2: Destinatär-Timeline, Nachweis-Board, Zahlungs-Pipeline & Pächter-Workflow
2a. Destinatär-Timeline (/destinataere/<pk>/timeline/)
- Chronologische Ansicht aller Events (Zahlungen, Nachweise, E-Mails, Notizen)
- Filter nach Typ via GET-Parameter
2b. Nachweis-Board (/nachweis-board/)
- Quartals-Übersicht aller aktiver Destinatäre (Q1–Q4) in einer Tabellenansicht
- Batch-Erinnerung: erzeugt Audit-Log-Einträge für säumige Destinatäre
- Semester-Logik erhalten (15.03 / 15.09 Fristen)
2c. Zahlungs-Pipeline (/zahlungs-pipeline/)
- 5-Stufen-Kanban: Offen → Nachweis eingereicht → Freigegeben → Überwiesen → Abgeschlossen
- Vier-Augen-Prinzip: can_be_freigegeben() prüft anderen Nutzer als Ersteller
- SEPA pain.001 XML-Export (/sepa-export/) für freigegebene Zahlungen
- Neue Status-Werte: nachweis_eingereicht, freigegeben, abgeschlossen
- Neue Felder: freigegeben_von, freigegeben_am, erstellt_von
2d. Pächter-Workflow (/paechter/workflow/)
- Pipeline nach Restlaufzeit: abgelaufen / <6M / 6–24M / >24M / unbefristet
- Ausstehende Jahresabrechnungen (Vorjahr ohne Abrechnung)
- Pachtanpassungen fällig (Verträge > 5 Jahre laufend)
- Top-Pächter nach Gesamtfläche
Sidebar-Navigation um Pipeline, Nachweis-Board und Pacht-Workflow erweitert.
Migration 0047 erzeugt und angewendet.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -1551,3 +1551,114 @@ def verpachtung_delete(request, pk):
|
||||
return render(request, 'stiftung/verpachtung_confirm_delete.html', context)
|
||||
|
||||
|
||||
# ============================================================
|
||||
# Phase 2d: Pächter-Workflow-Verbesserung
|
||||
# ============================================================
|
||||
|
||||
|
||||
@login_required
|
||||
def paechter_workflow(request):
|
||||
"""2d: Pipeline-Ansicht für Pächter – Vertragsfristen, Pachtanpassungen, Abrechnungen."""
|
||||
heute = date.today()
|
||||
|
||||
# Aktive Verpachtungen abrufen mit Restlaufzeit
|
||||
aktive_verpachtungen = LandVerpachtung.objects.filter(
|
||||
status="aktiv"
|
||||
).select_related("land", "paechter").order_by("pachtende")
|
||||
|
||||
# Kategorisieren
|
||||
abgelaufen = []
|
||||
demnachst = [] # < 6 Monate
|
||||
mittelfrisitig = [] # 6–24 Monate
|
||||
langfristig = [] # > 24 Monate
|
||||
kein_enddatum = []
|
||||
|
||||
for v in aktive_verpachtungen:
|
||||
if not v.pachtende:
|
||||
kein_enddatum.append(v)
|
||||
continue
|
||||
restlaufzeit = (v.pachtende - heute).days
|
||||
if restlaufzeit < 0:
|
||||
abgelaufen.append(v)
|
||||
elif restlaufzeit <= 180:
|
||||
demnachst.append(v)
|
||||
elif restlaufzeit <= 730:
|
||||
mittelfrisitig.append(v)
|
||||
else:
|
||||
langfristig.append(v)
|
||||
|
||||
# Ausstehende Jahresabrechnungen (letztes Jahr ohne Abrechnung)
|
||||
letztes_jahr = heute.year - 1
|
||||
laender_ohne_abrechnung = Land.objects.filter(
|
||||
aktiv=True
|
||||
).exclude(
|
||||
landabrechnung__abrechnungsjahr=letztes_jahr
|
||||
).order_by("lfd_nr")[:20]
|
||||
|
||||
# Pächter mit hoher Gesamtfläche (Top-Pächter)
|
||||
top_paechter = Paechter.objects.annotate(
|
||||
flaeche=Sum("landverpachtung__verpachtete_flaeche"),
|
||||
anzahl_vertraege=Count("landverpachtung")
|
||||
).filter(flaeche__gt=0).order_by("-flaeche")[:10]
|
||||
|
||||
# Anstehende Pachtanpassungen (> 5 Jahre laufend, keine Erhöhung dokumentiert)
|
||||
fuenf_jahre_ago = date(heute.year - 5, heute.month, heute.day)
|
||||
lang_laufend = LandVerpachtung.objects.filter(
|
||||
status="aktiv",
|
||||
pachtbeginn__lte=fuenf_jahre_ago,
|
||||
).select_related("land", "paechter").order_by("pachtbeginn")[:20]
|
||||
|
||||
pipeline_stages = [
|
||||
{
|
||||
"key": "abgelaufen",
|
||||
"label": "Abgelaufen / Handlungsbedarf",
|
||||
"farbe": "danger",
|
||||
"icon": "fa-exclamation-triangle",
|
||||
"verpachtungen": abgelaufen,
|
||||
"count": len(abgelaufen),
|
||||
},
|
||||
{
|
||||
"key": "demnachst",
|
||||
"label": "Bald fällig (< 6 Monate)",
|
||||
"farbe": "warning",
|
||||
"icon": "fa-clock",
|
||||
"verpachtungen": demnachst,
|
||||
"count": len(demnachst),
|
||||
},
|
||||
{
|
||||
"key": "mittelfristig",
|
||||
"label": "Mittelfristig (6–24 Monate)",
|
||||
"farbe": "info",
|
||||
"icon": "fa-calendar",
|
||||
"verpachtungen": mittelfrisitig,
|
||||
"count": len(mittelfrisitig),
|
||||
},
|
||||
{
|
||||
"key": "langfristig",
|
||||
"label": "Langfristig (> 24 Monate)",
|
||||
"farbe": "success",
|
||||
"icon": "fa-check",
|
||||
"verpachtungen": langfristig,
|
||||
"count": len(langfristig),
|
||||
},
|
||||
{
|
||||
"key": "unbefristet",
|
||||
"label": "Unbefristet / Kein Enddatum",
|
||||
"farbe": "secondary",
|
||||
"icon": "fa-infinity",
|
||||
"verpachtungen": kein_enddatum,
|
||||
"count": len(kein_enddatum),
|
||||
},
|
||||
]
|
||||
|
||||
context = {
|
||||
"pipeline_stages": pipeline_stages,
|
||||
"laender_ohne_abrechnung": laender_ohne_abrechnung,
|
||||
"top_paechter": top_paechter,
|
||||
"lang_laufend": lang_laufend,
|
||||
"letztes_jahr": letztes_jahr,
|
||||
"heute": heute,
|
||||
}
|
||||
return render(request, "stiftung/paechter_workflow.html", context)
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user