Project_Manager/app/projects/helpers.py
2026-06-26 18:21:22 +02:00

70 lines
2.3 KiB
Python

"""Hilfsfunktionen des Projekte-Moduls.
Enthält die feste Farbpalette (zyklisch zugewiesen), die Fälligkeits-Badge-Logik
(portiert aus dem Prototyp `dueBadge`), die Aufgaben-Sortierung und ein
locale-unabhängiges deutsches Datumslabel.
"""
from datetime import date
# Feste Palette wie im Prototyp — neue Projekte bekommen zyklisch die nächste Farbe.
PROJECT_COLORS = [
"#e94560", "#f5a623", "#4ecca3", "#a78bfa", "#60a5fa",
"#f472b6", "#34d399", "#fb923c", "#818cf8", "#38bdf8",
]
_WEEKDAYS_DE = [
"Montag", "Dienstag", "Mittwoch", "Donnerstag", "Freitag", "Samstag", "Sonntag",
]
_MONTHS_DE = [
"Januar", "Februar", "März", "April", "Mai", "Juni",
"Juli", "August", "September", "Oktober", "November", "Dezember",
]
def next_color(existing_count: int) -> str:
"""Nächste Farbe aus der Palette (zyklisch nach Anzahl vorhandener Projekte)."""
return PROJECT_COLORS[existing_count % len(PROJECT_COLORS)]
def _fmt(d: date) -> str:
"""Datum als dd.mm.yy (wie im Prototyp)."""
return f"{d.day:02d}.{d.month:02d}.{str(d.year)[2:]}"
def due_badge(due: date | None, done: bool) -> dict:
"""Fälligkeits-Badge: CSS-Klasse + Text. Portiert aus dem Prototyp.
- kein Datum -> 'kein Datum' (neutral)
- erledigt -> Datum neutral
- überfällig -> rot, mit Tagen drüber
- <= 7 Tage -> orange, mit Resttagen
- sonst -> grün
"""
if due is None:
return {"cls": "due-none", "text": "kein Datum"}
label = _fmt(due)
if done:
return {"cls": "due-none", "text": label}
diff = (due - date.today()).days
if diff < 0:
return {"cls": "due-overdue", "text": f"{label} ({abs(diff)}d über)"}
if diff <= 7:
return {"cls": "due-soon", "text": f"{label} ({diff}d)"}
return {"cls": "due-ok", "text": f"📅 {label}"}
def sort_tasks(tasks: list) -> list:
"""Sortierung wie im Prototyp: offen vor erledigt, dann nach Datum (ohne zuletzt)."""
return sorted(
tasks,
key=lambda t: (t.done, t.due_date is None, t.due_date or date.max),
)
def today_label() -> str:
"""Deutsches Datumslabel ohne Locale-Abhängigkeit (z.B. 'Donnerstag, 11. Juni 2026')."""
d = date.today()
return f"{_WEEKDAYS_DE[d.weekday()]}, {d.day}. {_MONTHS_DE[d.month - 1]} {d.year}"