- Mediathek: Video-Vorschaubilder statt Icons (FFmpeg-Thumbnails + Backfill-Command), Kategorie "Sonstiges" - B2in Media-Picker zeigt alle Medientypen, Typ wird automatisch erkannt; Thumbnail-Preview vor allen Medien-URL-Feldern - B2in Marke/Footer: Footer ein/aus, Logo+Claim frei positionierbar (Ecken) mit Constraints, separate Anzeige-Schalter - Angebote-Modul dynamisch: kein Slide-Typ mehr, einheitliches Detail-Layout mit ein-/ausblendbaren Bloecken, Logo/Brand pro Slide, Streichpreis-Option - Player: leere Module stoppen Endlosschleife, dynamische Layout-Anpassung bei verstecktem Footer/Header - Fix: Script-Ladereihenfolge (Livewire vor Flux), entfernte stale public/flux/flux.js, Modal-Crash beim Aktualisieren behoben Co-authored-by: Cursor <cursoragent@cursor.com>
23 KiB
Cabinet Displays – Implementierungs-Status
Konzept: siehe
00-entwicklungskonzept.md. Diese Datei wird je Phase fortgeschrieben.
Übersicht
| Phase | Inhalt | Status |
|---|---|---|
| 0 | Konzept-Freigabe | ✅ 11.05.2026 |
| 1 | Datenmodell + Daten-Migration | ✅ 11.05.2026 |
| 2 | API & Player (config + preview + module preview) | ✅ 12.05.2026 |
| 3 | Admin-UI: Displays-Liste mit Live/Entwurf | ✅ 12.05.2026 |
| 4 | Admin-UI: Entwurf-Editor (Iframe-Vorschau) | ✅ 12.05.2026 |
| 5 | Modul-Editor: 3-stufige Vorschau | ✅ 12.05.2026 |
| 6 | Umbenennung Versionen → Module + Onboarding | ✅ 12.05.2026 |
| 7 | Aufräumen + alte Pivot-Tabelle entfernen | ✅ 13.05.2026 |
| 8 | Review: Fehler / Optimierungen / Erweiterungen | 🟡 29.05.2026 (Befundaufnahme) |
Legende: ✅ fertig · 🟡 in Arbeit · ⏳ offen · ⛔ blockiert
Defaults aus §10 (Konzept-Freigabe vom 11.05.2026)
Der User hat das Konzept freigegeben. Da keine abweichende Wahl getroffen wurde, gelten die im Konzept empfohlenen Defaults:
- Test-Display: genau 1 Datensatz per Seeder angelegt, weitere können bei Bedarf erstellt werden.
- Entwurf verwerfen: löscht die Draft-Playlist. Beim erneuten Anlegen wird die Reihenfolge aus Live kopiert.
- Module bleiben shared: Modul-Änderungen wirken sofort auf alle Displays, die das Modul live einsetzen. Modul-eigene Versionierung ist out of scope.
- Polling-Mechanismus der Player (alle 60 s) reicht; kein Push-Refresh.
Live-Roll-out Hinweise
Auf dem Live-Server reicht für jede Phase:
git pull
composer install --no-dev --optimize-autoloader # falls neue Composer-Deps
php artisan migrate --force # bringt neue Migrations ein
php artisan config:cache # Caches frisch
php artisan view:clear
Alle strukturellen Änderungen liegen ausschließlich in database/migrations/ als datierte Dateien vor – auf der Live-DB reicht php artisan migrate --force. Datenverlust gibt es nicht: bestehende Pivot-Daten aus display_display_version werden in die neue Struktur überführt.
Phase 1 – Datenmodell
Ziel: neue Tabellen display_playlists + display_playlist_items, erweiterte displays-Spalten (is_test, preview_token), vollständige verlustfreie Migration der heutigen Pivot-Daten.
Dateien:
database/migrations/2026_05_11_*_create_display_playlists_table.phpdatabase/migrations/2026_05_11_*_create_display_playlist_items_table.phpdatabase/migrations/2026_05_11_*_add_test_flag_and_preview_token_to_displays_table.phpdatabase/migrations/2026_05_11_*_migrate_pivot_to_display_playlists.phpapp/Models/DisplayPlaylist.phpapp/Models/DisplayPlaylistItem.phpapp/Models/Display.php(neue Relations, alteversions()bleibt kompatibel)database/factories/DisplayPlaylistFactory.phpdatabase/factories/DisplayPlaylistItemFactory.phptests/Feature/DisplayPlaylistMigrationTest.php
Wichtig: Die alte Tabelle display_display_version und die Relation Display::versions() bleiben in dieser Phase erhalten (Removal erst in Phase 7), damit keine bestehenden Funktionen brechen.
Stand 11.05.2026 – ✅ abgeschlossen
Gelieferte Migrationen (Live-Reihenfolge)
| Reihenfolge | Datei | Zweck |
|---|---|---|
| 1 | 2026_05_11_113300_add_test_flag_and_preview_token_to_displays_table.php |
displays.is_test + displays.preview_token (unique) |
| 2 | 2026_05_11_113310_create_display_playlists_table.php |
Neue Tabelle für Live/Entwurfs-Bespielung pro Display |
| 3 | 2026_05_11_113320_create_display_playlist_items_table.php |
Geordnete Module pro Bespielung |
| 4 | 2026_05_11_113330_migrate_pivot_to_display_playlists.php |
Übernimmt bestehende Pivot-Daten als Published-Playlists (idempotent) |
Die Daten-Migration ist idempotent – wenn pro Display bereits eine Published-Playlist existiert, wird sie übersprungen. Die alte Pivot-Tabelle display_display_version bleibt erhalten.
Neue Modelle & Relations
App\Models\DisplayPlaylistmit Scopespublished()/draft(), Relationmodules()(geordnet)App\Models\DisplayPlaylistItemApp\Models\Displayerweitert umplaylists(),livePlaylist(),draftPlaylist(),liveModules(),ensurePreviewToken()Display::versions()ist als@deprecatedmarkiert, bleibt aber funktional
Tests
tests/Feature/DisplayPlaylistMigrationTest.php – 11 passed
tests/Feature/DisplayListTest.php – ok
tests/Feature/DisplayVersionTest.php – ok
tests/Feature/DisplayVersionApiTest.php – ok
tests/Feature/DisplayMediaTest.php – ok
Insgesamt 67 grüne Tests rund um Displays (11 neu + 56 bestand). Keine Linter-Warnungen, Pint clean.
Roll-out auf Live
git pull
php artisan migrate --force
Reihenfolge stimmt durch die Timestamps automatisch. Daten-Migration ist idempotent, kann beliebig oft laufen.
Phase 2 – API & Player
Ziel: bestehende Player-Konfiguration liest künftig aus der Published-Playlist. Zusätzlich gibt es öffentliche Vorschau-Endpunkte für Display-Entwürfe per Token und einzelne Module. Das JSON-Schema bleibt rückwärtskompatibel (playlist[], updated_at).
Stand 12.05.2026 – ✅ abgeschlossen
Geplante/aktuelle Dateien:
app/Services/DisplayPlaylistConfigBuilder.phpapp/Http/Controllers/Api/DisplayVersionApiController.phpapp/Http/Controllers/Api/DisplayPreviewController.phpapp/Http/Controllers/Api/ModulePreviewController.phproutes/domains.phppublic/_cabinet/display/index.htmltests/Feature/DisplayVersionApiTest.php
Umsetzung:
- Live-Config:
GET /api/display/{display}/configliestlivePlaylist - Live-Check:
GET /api/display/{display}/checkbezieht sich auf die Published-Playlist - Draft-Preview:
GET /api/display/preview/{token}liefert die Draft-Playlist - Modul-Preview:
GET /api/display/module/{module}/previewliefert ein Einzelmodul im Player-Schema - Player-Preview-Seiten:
/preview/{token}und/preview/module/{module}
Tests
tests/Feature/DisplayVersionApiTest.php – 13 passed
tests/Feature/DisplayPlaylistMigrationTest.php – ok
Insgesamt 24 grüne Tests für Phase 2 und die Playlist-Grundlage. Pint clean.
Hinweis
In der lokalen Umgebung musste der alte Route-Cache einmal mit php artisan route:clear geleert werden, damit die neuen Preview-Routen sichtbar wurden. Für Live bleibt beim Roll-out php artisan config:cache bzw. ein frischer Route-/Config-Cache relevant.
Phase 3 – Admin-UI: Displays-Liste mit Live/Entwurf
Ziel: Die Display-Liste zeigt pro physischem Display den Live-Stand und optionalen Entwurf nebeneinander. Entwürfe können aus Live angelegt, verworfen und veröffentlicht werden. Das Test-Display ist sichtbar hervorgehoben.
Stand 12.05.2026 – ✅ abgeschlossen
Dateien:
app/Livewire/Admin/Cms/DisplayList.phpresources/views/livewire/admin/cms/display-list.blade.phptests/Feature/DisplayListTest.php
Umsetzung:
- Display-Karten zeigen
LiveundEntwurfals zwei getrennte Spalten - Der globale Bearbeiten-Button im Display-Kopf wurde entfernt; Live und Entwurf haben jeweils eigene Bearbeiten-Buttons
- Die Live-Card zeigt die Player-URL direkt als kopierbares Feld; der API-Link ist weniger prominent unten rechts platziert
- Live-Spalte nutzt
livePlaylist.modules - Entwurf-Spalte nutzt
draftPlaylist.modules - Live-Bearbeitung speichert nur die Published-Playlist
- Entwurfs-Bearbeitung speichert nur die Draft-Playlist und erzeugt bei Bedarf den Preview-Token
- Die Modul-Auswahl im Bearbeiten-Dialog zeigt nur noch Module, die in der aktuell bearbeiteten Bespielung noch nicht enthalten sind
- Der Plus-Button fügt auch dann das erste verfügbare Modul hinzu, wenn der Select-Wert wegen des Platzhalters noch nicht explizit gesetzt wurde
- Aktion
Entwurf anlegenkopiert den aktuellen Live-Stand und erzeugt bei Bedarf den Preview-Token - Aktion
Veröffentlichenersetzt die Published-Playlist durch den Draft und synchronisiert die alte Pivot-Tabelle weiterhin kompatibel - Aktion
Verwerfenlöscht die Draft-Playlist - Test-Displays (
is_test) werden in der Liste hervorgehoben - Der bestehende Bearbeiten-Dialog pflegt die Live-Bespielung weiter und synchronisiert bis Phase 7 zusätzlich
display_display_version
Tests
tests/Feature/DisplayListTest.php – 14 passed
Die neuen Tests decken Draft anlegen, verwerfen, veröffentlichen, getrennte Live-/Entwurfs-Bearbeitung, gefilterte Modul-Auswahl sowie die Darstellung von Live-/Entwurf-Modulen ab.
Phase 4 – Admin-UI: Entwurf-Editor mit Iframe-Vorschau
Ziel: Beim Bearbeiten eines Entwurfs ist die Player-Vorschau direkt sichtbar. Moduländerungen im Entwurf werden sofort in die Draft-Playlist geschrieben und laden die Vorschau neu.
Stand 12.05.2026 – ✅ abgeschlossen
Dateien:
app/Livewire/Admin/Cms/DisplayList.phpresources/views/livewire/admin/cms/display-list.blade.phptests/Feature/DisplayListTest.php
Umsetzung:
- Der Entwurfs-Editor zeigt rechts eine 9:16-Iframe-Vorschau
- Die Iframe-Vorschau sitzt dauerhaft unterhalb der Aktualisieren-Aktion, damit sie im Desktop-Modal nicht mit dem Formular überlappt
- Die Vorschau lädt
/preview/{token}mit Cache-Bust-Parameter - Hinzufügen, Entfernen und Sortieren von Modulen persistiert bei Draft-Bearbeitung sofort in
display_playlist_items - Nach jeder Moduländerung wird die Iframe-Vorschau per
wire:keyneu aufgebaut - Vollbild-Vorschau ist aus dem Editor heraus verlinkt
Tests
tests/Feature/DisplayListTest.php – 21 passed
Die Tests decken das Rendern der Vorschau-URL und das sofortige Persistieren von Draft-Änderungen für Preview-Reloads ab.
Phase 5 – Modul-Editor: 3-stufige Vorschau
Ziel: Module können beim Bearbeiten visuell geprüft werden: kleine Vorschau je Item, eingebettete Player-Vorschau und Vollbild-Vorschau.
Stand 12.05.2026 – ✅ abgeschlossen
Dateien:
app/Livewire/Admin/Cms/DisplayVersionEditor.phpresources/views/livewire/admin/cms/display-version-editor.blade.phpresources/views/livewire/admin/cms/partials/version-editor-video.blade.phpresources/views/livewire/admin/cms/partials/version-editor-b2in.blade.phpresources/views/livewire/admin/cms/partials/version-editor-offers.blade.phptests/Feature/DisplayVersionTest.php
Umsetzung:
- Modul-Editor zeigt eine 9:16-Iframe-Vorschau über
/preview/module/{module} - Vollbild-Vorschau ist direkt aus dem Editor verlinkt
- Das Item-Bearbeiten-Modal ist breiter und zeigt unterhalb der Aktualisieren-Aktion ebenfalls eine 9:16-Iframe-Vorschau
Aktualisierenim Item-Bearbeiten-Modal schließt das Modal nicht mehr, sondern speichert den Inhalt und lädt die Iframe-Vorschau neu- Die Modal-Aktionen stehen unterhalb der Iframe-Vorschau und bieten
Aktualisieren,AbbrechenundSchließen - Die Vorschau im Item-Bearbeiten-Modal nutzt eine eigene Item-Preview und zeigt nur den aktuell bearbeiteten Slide statt das komplette Modul
- Der Display-Player rendert seinen Viewport strikt als 9:16-Fläche und skaliert Slide-, Footer- und QR-Elemente proportional zur Player-Fläche
- Harte Player-Elemente wie B2in-Headerlogo/Claim/Footer/QR, Offers-Logo/Brandtext/QR-Labels und Video-Footer-QR-Label sind jetzt als Modul-Einstellungen im CMS pflegbar
- Die Modul-Meta-Einstellungen sind als sichtbarer Block unterhalb der Media-/Slide-Liste editierbar; Angebote vererben Footer-Claim und Web/QR-URL automatisch an alle Slides
- Logo-Alt-Text-Felder wurden aus den Modul-Meta-Einstellungen entfernt; Player nutzen weiterhin feste Fallback-Alt-Texte
- Video-Display unterstützt Mediathek-Upload-URLs wie
/storage/...ohne Legacy-assets/-Prefix - Die Display-Mediathek und der schnelle Media-Picker akzeptieren SVG-Dateien als Bild-Uploads
- Änderungen an Name, Einstellungen, Items, Reihenfolge und Aktiv-Status laden die Modul-Vorschau neu
- Video/Footer/Media/Slide-Listen zeigen Inline-Mini-Previews je Item; Slide-Previews sind größer dargestellt
- Einzelmodul-Vorschau nutzt weiterhin den Player aus Phase 2
Phase 6 – Umbenennung Versionen → Module + Onboarding
Ziel: Die Admin-UI verwendet den fachlich korrekten Begriff „Module“. Alte URLs wurden während der Übergangsphase per 301 weitergeleitet und in Phase 7 entfernt.
Stand 12.05.2026 – ✅ abgeschlossen
Dateien:
routes/admin.phpapp/Livewire/Admin/Cms/DisplayVersionList.phpresources/views/livewire/admin/cms/display-version-list.blade.phpresources/views/livewire/admin/cms/display-version-editor.blade.phpresources/views/livewire/admin/cms/display-dashboard.blade.phpresources/views/components/layouts/app/sidebar.blade.phptests/Feature/DisplayVersionTest.php
Umsetzung:
- Neue Routen:
admin/cms/display-modulesundadmin/cms/display-modules/{displayVersion}/edit - Neue Routennamen:
admin.cms.display-modulesundadmin.cms.display-module-edit - Alte
display-versions-Routen waren während der Übergangsphase als 301-Redirects aktiv und wurden in Phase 7 entfernt - Sidebar, Dashboard, Listen- und Editor-Texte verwenden „Module“
- Technische Modell-/Klassennamen bleiben bei
DisplayVersion, da sie fachlich weiterhin die wiederverwendbaren Module abbilden
Tests
tests/Feature/DisplayVersionTest.php – ok
tests/Feature/DisplayVersionApiTest.php – ok
tests/Feature/DisplayListTest.php – ok
tests/Feature/DisplayPlaylistMigrationTest.php – ok
Insgesamt 64 grüne Tests für Phasen 5/6 und die angrenzenden Display-Flows. Pint clean.
Phase 7 – Technisches Aufräumen & Optimierung
Ziel: Nach Stabilisierung des neuen Playlist-Flows wird die alte Pivot-Kompatibilität entfernt und der Modul-Editor weiter vereinheitlicht.
Stand 13.05.2026 – ✅ umgesetzt
Dateien:
app/Models/Display.phpapp/Models/DisplayVersion.phpapp/Livewire/Admin/Cms/DisplayList.phpapp/Console/Commands/MigrateLegacyDisplays.phpapp/Support/DisplayModuleSettings.phpapp/Services/DisplayPlaylistConfigBuilder.phpapp/Livewire/Admin/Cms/DisplayVersionEditor.phpapp/Livewire/Admin/Cms/DisplayVersionList.phproutes/admin.phpdatabase/migrations/2026_05_13_103600_drop_display_display_version_table.phpresources/views/livewire/admin/cms/display-list.blade.phpresources/views/livewire/admin/cms/display-version-editor.blade.phpresources/views/livewire/admin/cms/partials/version-editor-video.blade.php
Umsetzung:
- Alte Pivot-Tabelle
display_display_versionwird per Migration entfernt - Legacy-Relationen
Display::versions()undDisplayVersion::displays()wurden entfernt - Display-Bearbeitung, Draft-Veröffentlichung und Legacy-Migrations-Command schreiben ausschließlich in
display_playlistsunddisplay_playlist_items - Alte
display-versions-Redirect-Routen wurden entfernt; die Admin-UI nutzt nur nochdisplay-modules - Modul-Settings-Defaults liegen zentral in
App\Support\DisplayModuleSettingsund werden von Editor, Listen-Erstellung und API-Config-Builder gemeinsam genutzt - Admin-Iframes laden per
loading="lazy"verzögert, um die parallelen Player-Vorschauen leichter zu halten - Video-Display-Items zeigen im Editor sichtbar an, ob die Quelle aus der Mediathek oder aus einem Legacy-Dateinamen kommt
Phase 8 – Review 29.05.2026 (Befundaufnahme)
Geprüft wurden die drei Navigationspunkte:
admin/cms/display-media→ Voltadmin.cms.display-media-libraryadmin/cms/display-modules→App\Livewire\Admin\Cms\DisplayVersionList(+ EditorDisplayVersionEditor)admin/cms/displays→App\Livewire\Admin\Cms\DisplayList
Vorgehen: Code-Review der Komponenten/Views/Services/Player + Laravel-Logs + DB-Stand. Eine Browser-Sichtprüfung war in dieser Session nicht möglich (Browser-MCP nicht verfügbar). Alle Befunde (#1–#11) wurden inzwischen umgesetzt (Details je Punkt unten).
Aktueller Datenstand (DB): 5 Displays (davon 0 Test-Displays), 6 Module, 7 Playlists (5 Live + 2 Entwürfe), 13 Medien.
Tests: DisplayListTest, DisplayMediaTest, DisplayVersionTest, DisplayVersionApiTest, DisplayPlaylistMigrationTest → 95 passed (276 Assertions). Keine CMS-Fehler in storage/logs (vorhandene Log-Fehler betreffen unrelated immobilien-azizi-Routen).
🔴 Fehler (sollten behoben werden)
-
Mediathek-Suche hebelt alle Filter aus. ✅ behoben 29.05.2026 In
display-media-library.blade.php($media-Computed) und inDisplayMediaPicker::resolveMediaItems()wurde die Suche als->where('filename','like',…)->orWhere('title','like',…)ohne Gruppierung an die vorherigenwhen()-Filter gehängt. Durch SQL-Präzedenz (ANDbindet stärker alsOR) wurde die Query zu… AND filename LIKE … OR title LIKE …. Sobald gesucht wurde, wurden Typ-, Quelle-, Sammlungs- und (beim Picker) deractive()-Filter ignoriert, sobald ein Treffer übertitlezustande kam. Behebung: Neuer gekapselter ScopeDisplayMedia::scopeSearch()(Closure umfilename/title), den Library und Picker gemeinsam nutzen. Tests:keeps preceding filters when combined with the search scope,search scope respects the active filter on the media pickerinDisplayMediaTest.php. -
Inhalt-Bearbeiten reaktiviert deaktivierte Items. ✅ behoben 29.05.2026 In
DisplayVersionEditorübergabloadItemContent()nur dascontent-Array anloadVideoContent()/loadFooterContent()/loadMediaContent()/loadSlideContent(). Alle vier setzten…IsActive = truefest – das tatsächlicheis_activedes Items wurde nie geladen. Wer ein zuvor per Auge-Icon deaktiviertes Item öffnete und „Aktualisieren" klickte, hat es übergetActiveFlag()ungewollt wieder aktiviert. Behebung:loadItemContent()reicht(bool) $item->is_activean die Loader durch, die es in die jeweilige…IsActive-Property schreiben. Test:editing an inactive item keeps it inactiveinDisplayVersionTest.php.
🟡 Optimierungen / Aufräumen
-
Toter Code im Video-Editor. ✅ behoben 29.05.2026
DisplayVersionEditor::loadAvailableVideos(), Property$availableVideos, dermount()-Aufruf und der ungenutzteIlluminate\Support\Facades\File-Import wurden entfernt (im aktiven Editor-Blade ungenutzt; das einzige Blade mitavailableVideosgehört zur Legacy-CabinetDisplay). Spart den Dateisystem-Scan vonpublic/_cabinet/assetsbei jedem Editor-Aufruf. -
Modul-Löschen ohne Schutz. ✅ behoben 29.05.2026
DisplayVersionList::deleteVersion()ermittelt jetzt dendisplays_count(distinct Displays über Playlists) und blockiert das Löschen, solange das Modul in irgendeiner Bespielung (Live oder Entwurf) genutzt wird; es erscheint ein roter Flash-Hinweis mit Anzahl. Module ohne Nutzung lassen sich weiterhin löschen. Test:cannot delete a display version that is used by a playlistinDisplayVersionTest.php. -
Doppelte Such-Logik zwischen Library und Picker (siehe #1) → ein gemeinsamer Query-Scope
DisplayMedia::scopeSearch(string $term)verhindert künftige Divergenz. ✅ erledigt 29.05.2026 (im Zuge von #1). -
Preview-Token bleibt nach Veröffentlichen bestehen. ✅ behoben 29.05.2026
DisplayList::publishDraft()/discardDraft()ließendisplays.preview_tokengesetzt, obwohl/preview/{token}danach 404 lieferte (kein Draft mehr); ein Rotations-Button fehlte ganz. Behebung: Neue Model-MethodenDisplay::rotatePreviewToken()undDisplay::clearPreviewToken().publishDraft()unddiscardDraft()setzen den Token jetzt zurück (alter Link wird ungültig). Im Entwurf gibt es einen „Link erneuern"-Button (rotatePreviewToken()mitwire:confirm), der bei offenem Entwurf zugleich die Iframe-Vorschau aktualisiert. Tests:publishing a draft clears the preview token,can discard a draft playlist(erweitert) undcan rotate the preview token of a draftinDisplayListTest.php.
🟠 Konfiguration / Dev-Umgebung
- Live-Vorschau zeigt im lokalen Dev auf die Produktion. ✅ behoben 29.05.2026
config/display.phpplayer_urldefaultete aufhttps://cabinet.b2in.eu/display, undDISPLAY_PLAYER_URLwar in.envnicht gesetzt. Indisplay-list.blade.phpnutzten „Vorschau", „Live-URL zum Kopieren" und „Display-Übersicht öffnen" diese Produktions-URL, während die Entwurfs-„Test-URL" überurl('/preview/…')lokal lief. Lokal sah man Live also den Produktionsstand, Entwurf aber lokale Daten – inkonsistent und irreführend. Behebung: Player-Seite (public/_cabinet/display/) und die Display-API liegen auf der Portal-Domain, daher ist der Player lokal unterhttps://portal.b2in.test/_cabinet/displayerreichbar (der Player ermitteltBASE_URLauswindow.location.originund ruft die API auf derselben Domain auf)..env:DISPLAY_PLAYER_URL=https://portal.b2in.test/_cabinet/displaygesetzt (Config-Cache geleert)..env.example: dokumentiert (Live-Wert als Kommentar).phpunit.xml:DISPLAY_PLAYER_URL=https://cabinet.b2in.eu/displaygepinnt, damit die bestehenden URL-Tests (DisplayListTest,DisplayVersionApiTest) deterministisch gegen den Produktionswert prüfen, unabhängig von der lokalen.env.- Der Produktions-Fallback in
config/display.php(und damit das Live-Verhalten) bleibt unverändert.
🟢 Erweiterungen / Verbesserungen (UX)
-
Test-Display existiert nicht. ✅ behoben 29.05.2026 Neuer idempotenter
Database\Seeders\TestDisplaySeederlegt genau ein Test-Display an (überspringt, falls schon vorhanden) und ist imDatabaseSeederregistriert. In der Dev-DB wurde das Test-Display angelegt. Tests:seeds exactly one test display,is idempotent and does not create a second test displayinTestDisplaySeederTest.php. -
Externe Bilder ohne Thumbnail. ✅ behoben 29.05.2026 Grid, Listenansicht und Detail-Sidebar (
display-media-library.blade.php) rendern externe Bilder jetzt direkt via<img src="{{ external_url }}">(gemeinsame$thumbSrc-Logik: Upload-Thumbnail → sonstexternal_url). Nicht-Bild-Externe behalten das Link-Icon. Test:renders external image media with an inline thumbnailinDisplayMediaTest.php. -
Mediathek-Pagination ohne
resetPage. ✅ behoben 29.05.2026 Die Volt-Komponente nutzt jetztWithPaginationund Update-Hooks (updatedSearch/updatedFilterType/updatedFilterSource/updatedFilterCollection), die bei jeder Filter-/SuchänderungresetPage()aufrufen. Test:resets pagination to page one when a filter changesinDisplayMediaTest.php. -
Modul-Hinzufügen nur einzeln. ✅ behoben 29.05.2026 Der Bespielungs-Dialog (
display-list.blade.php) nutzt jetzt einen durchsuchbaren Flux-Listbox-Multi-Select (versionsToAdd) plus „Hinzufügen"-Button (addSelectedVersions()), der alle ausgewählten Module auf einmal übernimmt (Duplikate werden übersprungen). Die programmatischeaddVersion()-Methode bleibt für Einzel-Adds/Tests erhalten. Test:can add multiple modules to a playlist at onceinDisplayListTest.php.
Empfohlene Reihenfolge
- #1 + #2 (echte Fehler, klein, mit Tests) → 2. #7 (Dev-Konfiguration, blockiert lokales Testen) → 3. #3/#4/#5/#6 (Aufräumen/Robustheit) → 4. #8–#11 (UX-Erweiterungen). Jeder Punkt wird gemäß Projekt-Regeln mit Test abgesichert und mit Pint formatiert.
Stand 29.05.2026: Alle Befunde (#1–#11) sind umgesetzt, getestet und mit Pint formatiert.