Backend Sprint 2+3: Health-Modul, Multi-Dog Tagebuch, Pillow, Migrations

- database.py: diary_dogs + walk_participant_dogs Tabellen, idempotente
  Migration für Health-Felder (charge_nr, kosten, diagnose, …), Backfill
- routes/health.py: vollständiges Health-Modul (war Stub), CRUD für
  Impfung/Entwurmung/Tierarzt/Medikament/Gewicht/Allergie/Dokument
- routes/diary.py: Multi-Dog n:m via diary_dogs (dog_ids in allen Endpoints)
- routes/dogs.py: Foto-Upload konvertiert HEIC/PNG/WebP → JPEG via Pillow
- routes/poison.py: Resolve mit Grundauswahl + Soft-Delete (geloest_von/at/grund)
- ki.py: health_summary() für KI-Gesundheitsbericht
- main.py: /favicon.ico Route
- requirements.txt: Pillow 11.2.1 + pillow-heif 0.22.0
This commit is contained in:
rene 2026-04-13 19:29:51 +02:00
parent 96e7a97b52
commit 6f48ec581d
8 changed files with 570 additions and 52 deletions

View file

@ -113,13 +113,28 @@ async def upload_photo(
if not dog:
raise HTTPException(404, "Hund nicht gefunden.")
# Datei speichern
ext = os.path.splitext(file.filename or "")[1] or ".jpg"
filename = f"dog_{dog_id}_{uuid.uuid4().hex[:8]}{ext}"
# Datei immer als JPEG speichern (HEIC/PNG/WebP → kompatibel für alle Browser)
import io
from PIL import Image
try:
import pillow_heif
pillow_heif.register_heif_opener()
except ImportError:
pass
content = await file.read()
try:
img = Image.open(io.BytesIO(content)).convert("RGB")
buf = io.BytesIO()
img.save(buf, format="JPEG", quality=90)
content = buf.getvalue()
except Exception:
pass # Fallback: Originaldaten speichern
filename = f"dog_{dog_id}_{uuid.uuid4().hex[:8]}.jpg"
path = os.path.join(MEDIA_DIR, "dogs", filename)
os.makedirs(os.path.dirname(path), exist_ok=True)
content = await file.read()
with open(path, "wb") as f:
f.write(content)