BuyingAgent/.specs/buying-agent-frontend-mvp-spec-v0.2.md

1330 lines
24 KiB
Markdown
Raw Normal View History

# Buying Agent – Frontend MVP Specification v0.2
**Status:** Review Candidate – vor Implementierung erneut durch den Coding-Agenten zu prüfen
**Spezifikationsversion:** 0.2
**Stand:** 2026-10-04
**Ersetzt vollständig:** `buying-agent-frontend-mvp-spec-v0.1.md`
**Gilt zusammen mit:**
1. `buying-agent-v0.1-spec-v1.1.md`
2. `buying-agent-architecture-addendum-v1.md`
3. `buying-agent-source-discovery-spec-v0.1.md`
Bei Widersprüchen innerhalb des Frontend-/MVP-Bereichs hat diese v0.2 Vorrang.
Sie präzisiert außerdem die für das Frontend notwendigen Backend-Verträge.
---
# 1. Zielbild
Der Buying Agent soll nicht nur ein Backend-Skeleton sein, sondern als **nutzbare PWA** einen vollständigen vertikalen Nutzerfluss abbilden.
Der Nutzer soll ohne technische Kenntnisse:
```text
BuyingProject anlegen
↓
Produktkategorie auswählen
↓
verfügbare Kriterien aus der Source-Taxonomie laden
↓
gewünschte Suchparameter auswählen und Werte setzen
↓
externe Suche generieren
↓
SearchRun starten / Status verfolgen
↓
Kandidaten sehen
↓
Shortlist / Ranking sehen, soweit konfiguriert
↓
Kandidat öffnen
↓
Attribute, Preise, Historie und bisherigen Status sehen
↓
Kriterien anpassen
↓
neue Suche ausführen
```
Die Oberfläche soll einfach bleiben. Die technische Komplexität verbleibt im Backend.
---
# 2. Grundsätzliche Architektur
## 2.1 Backend bleibt System of Record
Das Frontend enthält keine fachliche Kernlogik.
Es konsumiert ausschließlich die versionierte `/api/v1`-API.
Fachliche Entscheidungen über:
- Taxonomie
- Mapping
- Query-Generierung
- Produktidentität
- Diffing
- Ranking
- Historisierung
- Lifecycle
liegen im Backend.
## 2.2 Keine Canonical-Criteria-Schicht
Es wird **keine separate globale Canonical-Criteria-Ontologie** eingeführt.
Für eine unterstützte Source/Kategorie bildet deren gelernte Taxonomie zunächst den primären Kriterienkatalog.
Jedes Source-Kriterium erhält lediglich eine stabile interne ID:
```text
CriterionDefinition.id = interne UUID
```
Diese ID dient als Persistenz- und Referenzidentität.
Sie ist keine Behauptung, dass das Kriterium global quellenunabhängig kanonisch sei.
## 2.3 Source-Kriterien und Ergebnisattribute werden verbunden
Ein Kriterium muss sowohl mit dem Suchfilter als auch mit den aus Suchergebnissen bzw. Produktdetailseiten extrahierten Attributen verbunden werden können.
Beispiel:
```text
CriterionDefinition
id = <uuid>
origin = SOURCE
source = geizhals
category = notebook
label = "Arbeitsspeicher"
SourceFilterMapping:
Geizhals Filter 17023 -> CriterionDefinition.id
SourceAttributeMapping:
"RAM" -> CriterionDefinition.id
"Arbeitsspeicher" -> CriterionDefinition.id
ggf. source_attribute_id -> CriterionDefinition.id
```
Eine Produktbeobachtung soll dann auf dieselbe interne CriterionDefinition referenzieren:
```text
ProductAttributeObservation
- source_product_reference_id
- criterion_definition_id
- raw_name
- raw_value
- normalized_value
- unit
- observed_at
```
## 2.4 INTERNAL-Kriterien
Zusätzliche interne Kriterien werden nur angelegt, wenn für die Kaufentscheidung relevante Eigenschaften von der Source-Taxonomie nicht angeboten werden.
Beispiele:
- externer Akku-Benchmark
- Reparierbarkeit
- Testscore
- Lautstärke unter Last
```text
CriterionDefinition.origin = INTERNAL
```
Diese besitzen naturgemäß keinen Source-Filter, können aber später von anderen Datenquellen befüllt werden.
---
# 3. Produktkategorien
Das BuyingProject referenziert eine interne `ProductCategory`.
Beispiel:
```text
ProductCategory
id = notebook
name = Notebooks
```
Die Source-spezifische Kategorie wird separat gemappt:
```text
SourceCategory
source = geizhals
external_category_key = nb
product_category_id = notebook
```
Damit ist das BuyingProject nicht direkt an `geizhals/nb` gekoppelt.
---
# 4. BuyingProject
Ein BuyingProject ist die konkrete Instanz eines Kaufvorhabens.
Es kann **ohne ProductProfile** angelegt werden.
Mindestens:
```text
id
workspace_id nullable
name
product_category_id
market
currency
budget_target nullable
budget_maximum nullable
shortlist_size
schedule_interval_minutes
status
created_at
updated_at
archived_at nullable
```
Status:
```text
ACTIVE
PURCHASED
ARCHIVED
```
Default:
```text
shortlist_size = 5
schedule_interval_minutes = 180
```
---
# 5. Rolle von ProductProfile / BuyingTemplate
Das bisherige `ProductProfile` ist für neue BuyingProjects **nicht verpflichtend**.
Fachlich wird es künftig als optionale Vorlage verstanden.
Zielbild:
```text
BuyingTemplate
"Mobiler Entwicklungsrechner"
↓ optional beim Projektstart
BuyingProject
```
Eine Vorlage kann z. B. liefern:
- vorgeschlagene Suchkriterien
- Ranking-Konfiguration
- Default-Budget
- Kategorie
- Markt / Währung
Beim Erstellen eines Projekts werden relevante Werte in die Projektkonfiguration übernommen.
Spätere Änderungen an der Vorlage verändern bestehende Projekte **nicht rückwirkend**.
Zur Nachvollziehbarkeit darf gespeichert werden:
```text
template_id
template_version
```
Die bestehende ProductProfile-Implementierung darf technisch weiterverwendet werden, solange sie nicht mehr als zwingende Voraussetzung für ein BuyingProject fungiert.
---
# 6. ProjectCriteria
## 6.1 Zweck
ProjectCriteria beschreiben die vom Nutzer gewählten Suchparameter eines BuyingProjects.
Sie referenzieren die dynamisch geladenen CriterionDefinitions.
Beispiel:
```text
ProjectCriterion
- id
- project_id
- criterion_definition_id
- operator
- value
- enabled_for_discovery
- created_at
- updated_at
```
## 6.2 Standard-UI
Die Standardoberfläche zeigt **keine** technischen Ranking-Parameter wie:
- weight
- acceptable
- ideal
- strategy
- scoring_version
Der Nutzer wählt lediglich:
```text
Kriterium
Operator
Wert / Wertebereich
für externe Suche aktiv ja/nein
```
Optional kann später eine einfache Kennzeichnung wie „Muss“ / „Wunsch“ ergänzt werden, sie ist für v0.2 nicht Voraussetzung.
## 6.3 Beispiel
```text
Arbeitsspeicher >= 24 GB
Preis <= 1700 EUR
Gewicht <= 1.5 kg
```
Die verfügbaren Operatoren und UI-Controls werden aus der SourceFilterDefinition bzw. CriterionDefinition abgeleitet.
---
# 7. Ranking-Konfiguration
Discovery und Ranking bleiben getrennte fachliche Bereiche.
ProjectCriteria dürfen keine versteckten Scoring-Regeln erzwingen.
Ein Projekt kann optional eine Ranking-Konfiguration besitzen.
Mögliche Herkunft:
1. aus einem BuyingTemplate/ProductProfile übernommen
2. später explizit durch Advanced UI
3. später von KI vorgeschlagen
4. später durch eine Default-Strategie erzeugt
Für den MVP gilt:
- Ein Projekt ohne Ranking-Konfiguration darf trotzdem Discovery ausführen.
- In diesem Zustand zeigt das Frontend Kandidaten, aber kennzeichnet Ranking als `NOT_CONFIGURED`.
- Für den Notebook-Pilot kann das vorhandene Profil `mobile-development-notebook` als optionale Vorlage genutzt werden, damit ProductScore/Shortlist end-to-end getestet werden können.
- Es dürfen keine stillen, nicht dokumentierten Scoring-Regeln erfunden werden.
---
# 8. Criterion-Katalog vor Projektanlage
Der Projekt-Wizard muss Kriterien laden können, bevor eine Project-ID existiert.
Erforderliche Endpunkte:
```text
GET /api/v1/sources
GET /api/v1/sources/{source}/categories
GET /api/v1/sources/{source}/categories/{category}/available-criteria
```
`available-criteria` liefert mindestens:
```text
criterion_definition_id
label
description nullable
origin
source
category
filter_type
unit nullable
operators
options / range metadata
mapping_status
supports_discovery
```
Nur Source-Kriterien mit nutzbarer Filterdefinition werden als externe Suchparameter angeboten.
INTERNAL-Kriterien dürfen separat sichtbar sein, wenn sie für die Kategorie bekannt sind.
---
# 9. Taxonomie-Lernen
Taxonomie wird on demand pro Kategorie gelernt.
Initial:
```text
Geizhals -> Notebooks
```
Die gelernte Taxonomie soll später im Admin-Bereich bearbeitbar sein.
Mapping-Status:
```text
DISCOVERED
LEARNED_UNVERIFIED
VERIFIED
BROKEN
DISABLED
```
Nur `VERIFIED` darf automatisch für produktive Source-Query-Generierung verwendet werden.
Technisch eindeutige automatische Verifikation ist zulässig, wenn der Backend-Service einen reproduzierbaren Roundtrip sicher nachweisen kann.
---
# 10. DiscoverySearch
Persistenz bleibt **1:n**:
```text
BuyingProject
└── DiscoverySearch[]
```
Für den ersten MVP gilt als fachliche Einschränkung:
```text
maximal eine aktive DiscoverySearch
pro BuyingProject + Source + SourceCategory
```
Diese Einschränkung darf nicht als dauerhafte 1:1-Beziehung in das Datenmodell eingebaut werden.
Mindestens:
```text
id
buying_project_id
source_id
source_category_id
criteria_version
mapping_version
generated_url
status
schedule_interval_minutes
next_run_at nullable
last_successful_run_at nullable
created_at
updated_at
```
---
# 11. Statuswelten strikt trennen
## 11.1 Project Lifecycle
```text
ACTIVE
PURCHASED
ARCHIVED
```
## 11.2 DiscoverySearch / SearchRun Status
Je nach fachlicher Ebene:
```text
RUNNING
SUCCESS
PARTIAL
FAILED
BLOCKED
TOO_BROAD
OUT_OF_SYNC
```
`OUT_OF_SYNC` gehört fachlich zur Search-Konfiguration.
`TOO_BROAD` beschreibt den Zustand bzw. das Ergebnis einer DiscoverySearch/SearchRun-Ausführung.
## 11.3 Run Diff
```text
NEW
CHANGED
UNCHANGED
MISSING
```
## 11.4 Product Lifecycle
```text
ACTIVE
DISAPPEARED
ARCHIVED
```
## 11.5 Identity / Matching
```text
MATCHED
MATCH_UNCERTAIN
```
Diese Status dürfen in DB, API und UI nicht zu einem gemeinsamen Statusfeld vermischt werden.
---
# 12. Diff- und Lifecycle-Regeln
Nur vollständige erfolgreiche Full Runs dürfen fehlende Produkte ableiten.
```text
SUCCESS Full Run:
- NEW
- CHANGED
- UNCHANGED
- MISSING
```
`PARTIAL` darf **keine** MISSING-/DISAPPEARED-Transition auslösen.
Lifecycle:
```text
1 vollständiger Run fehlend -> MISSING im Run-Diff
3 aufeinanderfolgende vollständige Runs fehlend -> Product Lifecycle DISAPPEARED
```
Wiederauftauchen reaktiviert bestehende SourceProductReference, sofern Identity ausreichend sicher ist.
---
# 13. Candidate Summary DTO
Listen und Shortlist müssen genügend Daten liefern, damit das Frontend nicht für jede Zeile Einzelrequests benötigt.
Mindestens:
```text
candidate_id
source_product_reference_id
title
manufacturer nullable
model nullable
source_url
current_best_price nullable
currency nullable
current_dynamic_attributes
product_score nullable
product_eligibility nullable
ranking_status
shortlist_status
current_diff_status
product_lifecycle_status
match_status
first_seen_at
last_seen_at
```
`current_dynamic_attributes` ist metadata-driven und keine feste Notebook-Struktur.
---
# 14. Candidate Detail DTO
Erforderlicher Endpunkt:
```text
GET /api/v1/buying-projects/{project_id}/candidates/{candidate_id}
```
Mindestens:
```text
Candidate Summary
+
alle aktuellen normalisierten Attribute
+
Source-Metadaten
+
aktuelle Observation
+
Ranking-/Eligibility-Daten, soweit vorhanden
```
Das Frontend darf keine Gründe/Empfehlungen behaupten, die nicht tatsächlich persistiert sind.
---
# 15. Observation History
Erforderlicher Endpunkt:
```text
GET /api/v1/buying-projects/{project_id}/candidates/{candidate_id}/observations
```
Mindestens:
```text
observed_at
best_price
currency
availability nullable
seller_count nullable
dynamic_attributes
search_run_id
```
Diese Historie ermöglicht:
- Preisentwicklung
- Attributänderungen
- Last Seen
- Verlauf über SearchRuns
Kein HTML-Archiv.
---
# 16. Project Summary DTO
Die Projektliste soll nicht N+1-Requests erzeugen.
Erforderlich:
```text
GET /api/v1/buying-projects
```
Pro Projekt mindestens:
```text
id
name
product_category
status
last_successful_run_at nullable
next_run_at nullable
discovery_status nullable
candidate_count
shortlist_count
new_count
changed_count
missing_count
current_search_result_count nullable
```
---
# 17. Projekt-Wizard
Route:
```text
/projects/new
```
## Schritt 1 – Basis
```text
Projektname
Produktkategorie
Markt
Währung
Budget Ziel optional
Budget Maximum optional
Shortlist-Größe
Suchintervall
optional BuyingTemplate
```
## Schritt 2 – Kriterien laden
Nach Kategorieauswahl:
```text
GET available-criteria
```
Die UI zeigt die Source-Kriterien als verständliche Liste.
Beispiel Notebooks:
```text
[ ] Hersteller
[ ] Arbeitsspeicher
[ ] SSD
[ ] Gewicht
[ ] Displaygröße
[ ] CPU
[ ] Grafikkarte
...
```
## Schritt 3 – Parameter setzen
Nach Aktivierung eines Kriteriums:
```text
Arbeitsspeicher
Operator: mindestens
Wert: 24 GB
```
Control-Typen:
```text
BOOLEAN
ENUM
MULTI_ENUM
NUMERIC_RANGE
NUMERIC_THRESHOLD
TEXT
```
Das UI rendert dynamisch.
Keine hartcodierten Notebook-Felder.
## Schritt 4 – Projekt speichern
Erst jetzt wird das BuyingProject angelegt und die ProjectCriteria werden gespeichert.
---
# 18. Kriterienänderung im bestehenden Projekt
Route:
```text
/projects/:projectId/criteria
```
Ändert der Nutzer relevante ProjectCriteria:
```text
criteria_version++
DiscoverySearch.status = OUT_OF_SYNC
```
Das Frontend zeigt:
> Suchparameter wurden geändert. Die externe Suche muss aktualisiert werden.
Aktion:
```text
Suche aktualisieren
```
Backend:
```text
generate-query
→ VERIFIED Mappings verwenden
→ neue URL speichern
→ optional SearchRun starten
```
---
# 19. Hauptscreens
## 19.1 Projektliste
```text
/projects
```
Anzeige:
- Name
- Kategorie
- Project Lifecycle
- letzter erfolgreicher Run
- Discovery-Status
- Kandidatenzahl
- Shortlistzahl
- NEW / CHANGED Counts
- nächste Suche
## 19.2 Projektdetail
```text
/projects/:projectId
```
Bereiche:
```text
Übersicht
Kandidaten
Shortlist
Kriterien
Historie
```
## 19.3 Kandidaten
```text
/projects/:projectId/candidates
```
Desktop:
- Tabelle / kompakte Liste
Mobile:
- Cards / List Items
## 19.4 Kandidatendetail
```text
/projects/:projectId/candidates/:candidateId
```
Zeigt nur tatsächlich vorhandene Daten:
- Titel / Hersteller / Modell
- aktueller Preis
- dynamische Attribute
- Eligibility / ProductScore, soweit vorhanden
- Ranking Status
- Diff Status
- Product Lifecycle
- Match Status
- First Seen / Last Seen
- Observation History
Nicht anzeigen, solange Backend es nicht erzeugt:
- Deep-Enrichment-Ergebnisse
- Review-Zusammenfassungen
- finale Kaufentscheidung
- nicht persistierte Begründungen
## 19.5 Shortlist
```text
/projects/:projectId/shortlist
```
Zeigt Top-N, falls Ranking konfiguriert.
Ohne Ranking-Konfiguration:
```text
Ranking ist noch nicht konfiguriert.
```
## 19.6 Historie
```text
/projects/:projectId/history
```
SearchRuns mit:
```text
Zeitpunkt
Run Status
Trefferzahl
Page Count
NEW
CHANGED
MISSING
Fehler / BLOCKED / TOO_BROAD
```
---
# 20. Admin-Bereich
Routen:
```text
/admin/sources
/admin/sources/:source/categories
/admin/sources/:source/categories/:category
```
Funktionen:
- Kategorien sehen
- Taxonomie laden/neu laden
- SourceFilterDefinitions sehen
- Optionen / Ranges sehen
- CriterionDefinitions sehen
- SearchFilter-Mapping sehen
- SourceAttributeMappings sehen
- Mapping-Status ändern
- kleine Mapping-Korrekturen durchführen
- BROKEN / DISABLED erkennen
Technische IDs sind nur hier sichtbar.
Das Frontend generiert keine Source-URL-Encodings selbst.
---
# 21. Frontend-Technologie
Verbindlich:
- React
- TypeScript
- Vite
- PWA
- TanStack Query
- React Router oder vergleichbare schlanke Lösung
Nicht erforderlich:
- Next.js
- SSR
- SEO
Begründung:
Die Anwendung ist eine private/interne App und benötigt keine suchmaschinenoptimierte öffentliche Seitenauslieferung.
---
# 22. Responsive Architektur
Von Anfang an zwei bewusste Hauptlayouts.
## Desktop
```text
Sidebar + Hauptinhalt + optional Detailbereich
```
## Mobile
```text
Bottom Navigation / kompakte Navigation
+ Vollbild-Detailseiten
+ projektinterne Tabs
```
Keine bloße Verkleinerung des Desktop-Layouts.
---
# 23. Mitai-Bezug
Wenn der Mitai-Quellcode dem Coding-Agenten im Repository oder über einen konkret angegebenen Pfad zugänglich ist, sollen passende Muster wiederverwendet werden:
- PWA-Shell
- Responsive Breakpoints
- Navigation
- Layout
- ggf. Basiskomponenten
Ohne zugänglichen Pfad darf der Agent keine Annahmen über konkrete Mitai-Komponenten treffen.
Dann nur dieselben Architekturprinzipien umsetzen.
---
# 24. CORS
Backend muss den Frontend-Origin konfigurierbar zulassen.
Keine harte Produktions-URL im Code.
Beispiel:
```text
CORS_ALLOWED_ORIGINS
```
Lokale Entwicklung:
```text
http://localhost:<frontend-port>
```
Produktive Origins über Environment.
---
# 25. Docker Compose
Der nutzbare MVP enthält mindestens:
```text
api
postgres
frontend
```
Das Frontend muss über Compose startbar sein.
Development und Production Build dürfen unterschiedliche Docker Targets verwenden.
Root-Compose bleibt zentrale Startstelle.
---
# 26. CI
CI muss mindestens enthalten:
Backend:
- Unit Tests
- Integration Tests
- API E2E
Frontend:
- TypeScript typecheck
- lint
- unit/component tests
- production build
E2E:
- vollständiger Notebook-Pilot mit Fixture/Mock-Source
- Desktop viewport
- Mobile viewport
Live-Geizhals-Abfragen gehören nicht in CI.
---
# 27. PWA
Mindestens:
- Manifest
- installierbare App
- App Icons
- Responsive App Shell
- Offline-Fallback
Keine komplexe Offline-Synchronisation im MVP.
---
# 28. Loading / Empty / Error States
Jeder wesentliche Screen braucht:
```text
Loading
Empty
Error
Retry
```
Beispiele:
- Noch keine Projekte vorhanden.
- Noch keine Kandidaten gefunden.
- Noch kein SearchRun ausgeführt.
- Taxonomie wurde noch nicht geladen.
- Suche ist OUT_OF_SYNC.
- Suche wurde BLOCKED.
- Ranking ist nicht konfiguriert.
---
# 29. API-Verträge – Mindestumfang
## Projekte
```text
GET /api/v1/buying-projects
POST /api/v1/buying-projects
GET /api/v1/buying-projects/{id}
PATCH /api/v1/buying-projects/{id}
```
## Kriterien
```text
GET /api/v1/buying-projects/{id}/criteria
PUT /api/v1/buying-projects/{id}/criteria
```
## Source / Kategorien
```text
GET /api/v1/sources
GET /api/v1/sources/{source}/categories
POST /api/v1/sources/{source}/categories/{category}/discover-taxonomy
GET /api/v1/sources/{source}/categories/{category}/available-criteria
```
## Admin Mapping
```text
GET /api/v1/sources/{source}/categories/{category}/filters
GET /api/v1/criterion-mappings
POST /api/v1/criterion-mappings
PATCH /api/v1/criterion-mappings/{id}
GET /api/v1/source-attribute-mappings
POST /api/v1/source-attribute-mappings
PATCH /api/v1/source-attribute-mappings/{id}
```
## Discovery Search
```text
GET /api/v1/buying-projects/{id}/discovery-searches
POST /api/v1/buying-projects/{id}/discovery-searches
POST /api/v1/discovery-searches/{id}/generate-query
POST /api/v1/discovery-searches/{id}/run
```
## SearchRuns
```text
GET /api/v1/discovery-searches/{id}/runs
GET /api/v1/search-runs/{id}
```
## Candidates
```text
GET /api/v1/buying-projects/{id}/candidates
GET /api/v1/buying-projects/{id}/candidates/{candidateId}
GET /api/v1/buying-projects/{id}/candidates/{candidateId}/observations
GET /api/v1/buying-projects/{id}/shortlist
```
---
# 30. Nutzerfreundlichkeit
Die Standardoberfläche zeigt keine Begriffe wie:
```text
CriterionDefinition
SourceFilterDefinition
mapping_version
source_filter_id
normalized_spec_fingerprint
```
Stattdessen:
```text
Arbeitsspeicher
mindestens
24 GB
```
Technische Details gehören in den Admin-Bereich.
---
# 31. KI-Erweiterung – bewusst vorbereitet, nicht implementiert
Später soll KI den heute manuellen Kriterien-Auswahlschritt übernehmen können.
Ziel:
```text
Nutzer beschreibt Wunsch in natürlicher Sprache
↓
KI erhält verfügbare Source-Kriterien
↓
KI schlägt konkrete Filterparameter vor
↓
Nutzer bestätigt / korrigiert
↓
ProjectCriteria werden gespeichert
```
Wichtig:
Die KI soll Source-Kriterien möglichst aus dem tatsächlich verfügbaren Katalog auswählen.
INTERNAL-Kriterien dürfen nur vorgeschlagen werden, wenn sie im System bekannt sind und eine Datenquelle bzw. Bewertungsstrategie existiert.
Keine KI-Implementierung in v0.2.
---
# 32. Tests
## Frontend Unit / Component
- dynamischer Criteria Renderer pro Filtertyp
- Projekt-Wizard
- Mapping-/Statusdarstellung
- Candidate List
- Candidate Detail
- Mobile Navigation
- Desktop Navigation
- Loading / Empty / Error States
## API Integration
- Kategorie-Katalog laden
- available-criteria vor Projektanlage laden
- Projekt ohne Profil anlegen
- Projekt optional aus Template anlegen
- Criteria speichern
- Search generieren
- SearchRun starten
- Candidate Summary laden
- Candidate Detail laden
- Observation History laden
- Shortlist laden
## E2E Notebook-Pilot
```text
App öffnen
→ neues Projekt
→ Notebooks wählen
→ Geizhals-Kriterien laden
→ RAM >= 24 GB auswählen
→ Preismaximum setzen
→ Projekt speichern
→ Query generieren
→ SearchRun ausführen
→ Kandidaten anzeigen
→ Kandidat öffnen
→ dynamische Attribute sehen
→ Preis / Observation History sehen
→ Kriterien ändern
→ OUT_OF_SYNC sehen
→ Query neu generieren
```
Wenn optional ein Ranking-Template verwendet wird:
```text
→ ProductScore sichtbar
→ Shortlist sichtbar
```
## Responsive E2E
Mindestens:
- Desktop Viewport
- Mobile Viewport
---
# 33. Nicht Bestandteil dieses Slices
- Auth / Login
- RBAC
- Einladungen
- Multi-User UI
- Keepa
- Idealo
- LLM-Automation
- Deep Enrichment
- finale Decision Engine
- Kaufautomatisierung
- Warenkorb
- komplexe Benachrichtigungen
Die Architektur darf diese Erweiterungen nicht verbauen.
---
# 34. Definition of Done
## Architektur
- [ ] Keine separate Canonical-Criteria-Schicht.
- [ ] Source-Kriterien besitzen stabile interne CriterionDefinition-IDs.
- [ ] SearchFilter und Ergebnisattribute können auf dieselbe CriterionDefinition-ID gemappt werden.
- [ ] INTERNAL-Kriterien sind möglich.
- [ ] BuyingProject ist ohne ProductProfile anlegbar.
- [ ] ProductProfile kann optional als Vorlage dienen.
- [ ] DiscoverySearch-Persistenz bleibt 1:n-fähig.
- [ ] Statuswelten sind getrennt.
## API
- [ ] Source-Kategorie-Katalog existiert.
- [ ] available-criteria funktioniert vor Projektanlage.
- [ ] Candidate Summary DTO enthält Preis, Attribute, Diff, Lifecycle, last_seen und Ranking-Felder.
- [ ] Candidate Detail existiert.
- [ ] Observation History existiert.
- [ ] Project Summary DTO enthält Aggregate.
- [ ] CORS ist konfigurierbar.
## Frontend
- [ ] React + TypeScript + Vite.
- [ ] PWA installierbar.
- [ ] Desktop-Layout.
- [ ] Mobile-Layout.
- [ ] Projektliste.
- [ ] Projekt-Wizard.
- [ ] Kriterien dynamisch aus Source-Taxonomie.
- [ ] Keine notebook-spezifisch hartcodierten Criteria Controls.
- [ ] Projekt-Detail.
- [ ] Kandidatenliste.
- [ ] Kandidatendetail.
- [ ] Observation History.
- [ ] Shortlist, wenn Ranking verfügbar.
- [ ] Admin-Bereich für Taxonomie/Mappings.
- [ ] OUT_OF_SYNC sichtbar und korrigierbar.
- [ ] Loading / Empty / Error States.
## Integration
- [ ] Frontend in Docker Compose.
- [ ] Frontend Build/Tests in CI.
- [ ] Backend Tests grün.
- [ ] Frontend Tests grün.
- [ ] Desktop E2E grün.
- [ ] Mobile E2E grün.
- [ ] Notebook-Pilot über die UI erfolgreich.
---
# 35. Arbeitsauftrag an den Coding-Agenten
Diese Datei ersetzt `buying-agent-frontend-mvp-spec-v0.1.md` vollständig.
Bitte **noch nicht implementieren**.
Führe zunächst denselben Review-Prozess durch wie bei der v0.1:
1. Prüfe die aktuelle Repository-Implementierung gegen:
- `buying-agent-v0.1-spec-v1.1.md`
- `buying-agent-architecture-addendum-v1.md`
- `buying-agent-source-discovery-spec-v0.1.md`
- `buying-agent-frontend-mvp-spec-v0.2.md`
2. Prüfe insbesondere, ob die in deinem vorherigen Frontend-MVP-Review identifizierten Blocker F1–F6 und die weiteren Lücken mit v0.2 vollständig geschlossen sind.
3. Berichte ausschließlich:
- verbleibende echte fachliche Widersprüche,
- noch fehlende Verträge,
- technisch riskante Annahmen,
- notwendige Backend-Änderungen,
- notwendige Frontend-Änderungen.
4. Keine neue Fachlogik erfinden, um Lücken still zu schließen.
5. Wenn keine blockierenden Punkte mehr bestehen, erstelle einen aktualisierten Implementierungsplan für einen **vertikalen End-to-End-MVP**, sodass jeder Schritt über das Frontend prüfbar wird.
6. Implementierung erst nach ausdrücklicher Freigabe dieses Reviews.