ORDNERUEBERSICHT. Eine Spalte neben der Galerie mit allen Ordnern, auf allen
Ebenen, mit Anzahl und Groesse; ein Klick filtert. Neu dafuer:
- GET /api/dash/folders -- die Ordner werden in JavaScript zusammengezaehlt
und nicht in SQL: fuer eine Baumansicht braucht es JEDE Ebene, und das waere
in SQLite eine rekursive Abfrage, die niemand mehr liest.
- GET /api/dash/media?folder=... als EIGENER Filter neben der Suche. Die Suche
findet mit LIKE %...% auch "alt/vehicles/adder.webp"; ein Ordner, der Dinge
zeigt, die nicht darin liegen, ist keiner. Hier ist der Anfang verankert.
- Die LIKE-Sonderzeichen werden maskiert: ein Ordner "fotos_alt" wuerde sonst
auch "fotosXalt" treffen, weil _ in LIKE ein beliebiges Zeichen ist.
Die Zahlen sind kumulativ -- "vehicles" enthaelt, was in "vehicles/showroom"
liegt. Alles andere ueberrascht in einer Baumansicht. Nachgemessen ueber drei
Ebenen: vehicles (24) > showroom (2) > tief (1), Filter und Zaehlung stimmen,
und nach dem Aufraeumen steht wieder vehicles (22).
Flache Liste mit Einrueckung statt aufklappbarem Baum: bei einer Handvoll
Ordner ist ein Aufklappmechanismus mehr Bedienung als Nutzen -- und was man
nicht aufklappen muss, kann man auch nicht zugeklappt uebersehen.
Dazu: der NPM-Zwischenspeicher ist zu. Der Schnipsel steht im Feld "Custom
Nginx Configuration"; NPM setzt ihn innerhalb des server-Blocks ein, eine
location ist dort also gueltig. Nachgemessen: cache-control kommt wieder von
uns, und ein ueberschriebenes Bild ist sofort das neue.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Schritt 4. React 18, TypeScript, Vite 5, Tailwind 4 (CSS-first), Lucide,
Zustand; kein Konsta. Quelle in server/ui, Build nach server/web (gitignored),
im Abbild von einer eigenen Docker-Stufe gebaut.
JEDER KNOPF GIBT RUECKMELDUNG -- und zwar erzwungen, nicht vorgenommen:
- api.ts haelt den EINZIGEN fetch und GENAU EINE Fehlerklasse. Der
Fivemanage-Fehler war, zwei zu haben: geworfen wurde `new Error`, geprueft
auf `instanceof ApiError`, und damit verschwand jeder Fehlschlag lautlos.
- store.ts haelt run(): Aktion rein, Erfolgstext rein, und es meldet bei
Erfolg diesen und bei Fehlschlag den Text DES DIENSTES. Wer darueber geht,
kann keinen stillen Knopf bauen.
- Jeder wartende Knopf ist gesperrt und zeigt einen Kreisel. Der zweite Klick
eine Sekunde spaeter war der Weg zu neunzehn gleichnamigen Organisationen.
- Fehlermeldungen bleiben stehen, bis jemand sie wegklickt. Ein Fehler, der
von allein verschwindet, ist einer, den niemand gelesen hat.
@vitejs/plugin-react ist auf ^4 festgenagelt: die 6 verlangt vite ^8. In den
peerDependencies nachgesehen -- Vite 5.4.21 liegt in der Schnittmenge von
plugin-react@4 und @tailwindcss/vite@4.
Am laufenden Container nachgemessen: / kommt als text/html, assets/*.js als
text/javascript, *.css als text/css (die MIME-Falle aus Schritt 1 traegt), und
/tokens, /speicher, /konto liefern dieselbe index.html -- die SPA-Rueckfall-
route tut, wofuer sie gebaut wurde.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>