diff --git a/Plan.md b/Plan.md index 21fff31..008f61d 100644 --- a/Plan.md +++ b/Plan.md @@ -76,7 +76,7 @@ getarntes Skript ebenfalls. ## Datenmodell – Abweichungen von `projekt.md` -Das Schema wird grundsätzlich übernommen. Vier Ergänzungen: +Das Schema wird grundsätzlich übernommen. Fünf Ergänzungen: 1. **Feste Wertelisten statt freier VARCHAR.** `gender`, `season`, `condition` und `status` bekommen ein Python-Enum plus `CHECK`-Bedingung in der @@ -97,12 +97,65 @@ Das Schema wird grundsätzlich übernommen. Vier Ergänzungen: 4. **`updated_at`** wird in der Anwendung gesetzt, nicht per DB-Trigger – bleibt so unabhängig von SQLite-Eigenheiten. +5. **Status `draft` (neu).** `projekt.md` kennt nur `available`, `reserved` + und `given_away`. Der Stapel-Import (siehe unten) legt Einträge an, die + noch keinen Titel und keine Grösse haben – die dürfen nicht in der + öffentlichen Galerie erscheinen. `title` und `size` müssen dafür + `NULL` erlauben; gefüllt sein müssen sie erst beim Wechsel auf + `available`. + Ausserdem: beim Löschen eines Eintrags müssen die **Bilddateien mitgelöscht** werden, sonst wächst das Upload-Verzeichnis unbegrenzt mit verwaisten Dateien. `ON DELETE CASCADE` räumt nur die Datenbankzeilen weg, nicht die Dateien. --- +## Schnelles Erfassen + +Beim Erstbestand sind auf einen Schlag viele Teile zu erfassen. Der Aufwand +steckt dabei nicht im Fotografieren, sondern im Rundlauf pro Stück: Formular +öffnen, fotografieren, Felder ausfüllen, speichern, von vorn. Zwei Massnahmen +dagegen. + +### Stapel-Import + +Zuerst wird alles mit der gewohnten Kamera-App fotografiert – die ist fürs +schnelle Knipsen gebaut, ohne Umweg über den Browser. Danach **einmal** ins +Formular, alle Fotos auf einmal auswählen: + +```html + +``` + +Pro Foto entsteht ein Eintrag mit Status `draft`. Die Details werden später +nachgetragen – in Ruhe, auch am Rechner mit richtiger Tastatur. Damit ist +Fotografieren vom Erfassen entkoppelt. + +Bewusst **ohne** `capture="environment"`: das springt zwar direkt in die +Rückkamera, erzwingt aber ein Foto pro Vorgang und schliesst `multiple` aus. +Für einzelne Nachträge im Alltag ist es passend – dann als zweiter, kleiner +Knopf „Direkt fotografieren" neben dem regulären Feld. + +Nötig dafür: +- Ansicht „Unfertige Einträge (12)", nur für angemeldete Benutzer +- Entwürfe erscheinen nicht in der Galerie und nicht in `GET /api/v1/items`, + solange dort nicht ausdrücklich `status=draft` angefragt wird +- Ein Entwurf wird erst zu `available`, wenn Grösse und Kategorie gesetzt sind + +### Titel ist freiwillig + +`title` wird optional. Bleibt das Feld leer, setzt die Anwendung ihn aus +Kategorie und Grösse zusammen – „Hose 98/104", „Winterjacke 116". Das ist +genau die Angabe, nach der man in einer Galerie ohnehin sucht, und spart beim +Erfassen das mit Abstand lästigste Feld, weil es als einziges freien Text +verlangt. + +Erzeugt wird der Titel **beim Anzeigen**, nicht beim Speichern: sonst bliebe +ein automatisch gesetzter Titel stehen, wenn später die Grösse korrigiert +wird. In der Datenbank bleibt `title` dann schlicht `NULL`. + +--- + ## Absicherung Die App ist aus dem Internet erreichbar, also gelten hier andere Massstäbe als @@ -181,9 +234,15 @@ Die Phasen aus `projekt.md`, ergänzt um Tests und die Absicherung. **Phase 2 – Bilder** - Upload per `multipart/form-data`, mehrere Bilder pro Eintrag - Prüfung und WebP-Konvertierung (max. 1200 px Breite) nach Abschnitt 1 oben +- **HEIC unterstützen** (`pillow-heif`): iPhones nehmen in diesem Format auf. + Safari wandelt beim Hochladen über ein Datei-Feld meist selbst nach JPEG + um – aber nicht zuverlässig, und beim Stapel-Import fällt ein einzelnes + nicht lesbares Bild sonst still hinten runter. Pillow allein kann HEIC + nicht öffnen. - Ausliefer-Route, `is_primary`-Logik, Aufräumen beim Löschen - Prüfpunkt: bewusst fehlerhafte Uploads (zu gross, falscher Typ, riesige - Pixelmasse, `.php` als `.jpg` getarnt) werden alle abgewiesen + Pixelmasse, `.php` als `.jpg` getarnt) werden alle abgewiesen; ein + HEIC-Bild wird angenommen **Phase 3 – Absicherung** - Anmeldung, Sitzung, CSRF, Rate-Limits, Sicherheits-Header @@ -192,10 +251,12 @@ Die Phasen aus `projekt.md`, ergänzt um Tests und die Absicherung. **Phase 4 – Oberfläche** - Mobile-First-Layout, Galerie mit Filterleiste (HTMX) -- Detailseite, Erfassungsformular mit Kamera-Aufnahme - (``) +- Detailseite und Erfassungsformular +- **Stapel-Import** mit Entwurfsliste zum Nachtragen (siehe „Schnelles + Erfassen"), dazu der automatische Titel aus Kategorie und Grösse - Reservierungs-Ablauf inklusive Selbst-Freigabe -- Prüfpunkt: der ganze Weg auf einem echten Smartphone +- Prüfpunkt: der ganze Weg auf einem echten Smartphone – 20 Fotos in einem + Rutsch hochladen, danach die Entwürfe abarbeiten **Phase 5 – Betrieb** - `Dockerfile` (Tailwind-Build inbegriffen), `docker-compose.yml`, Volumes