Track HiveGrid Cloud planning reference
This commit is contained in:
1 parent
b3d5ea6764
commit
e341c5938a
5784 files changed
+1104929
-3
No files matched your search
@@ -0,0 +1,88 @@
|
||||
# M001 — Audit-Log default
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 1 (Bauprinzipien)
|
||||
**Bauprinzip:** A.6 — Audit-Log als Default
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/03-architektur.md` Sektion A.6
|
||||
|
||||
## Ziel
|
||||
Eine Schreib-Aktion durch ein beliebiges Modul erzeugt automatisch einen Audit-Eintrag — ohne dass das Modul den Audit-Service aktiv aufrufen muss.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.6.1 — Jede schreibende Aktion (Anlegen, Ändern, Löschen, Status-Wechsel) wird mit Wer/Wann/Was/Vor-Nach-Wert protokolliert
|
||||
- A.6.2 — Auch Aktionen durch Automatisierungen oder externe Sync-Vorgänge; Auslöser wird mit-protokolliert
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** EU-Sterilisation + RR7-Migration der Boilerplate abgeschlossen
|
||||
- **Wird benötigt von:** M004, M005, M006, M075-M082 (Automation), M151-M152 (Audit-UI/Export), alle schreibenden Module
|
||||
|
||||
## Out of Scope
|
||||
- Audit-Anzeige-UI → M151
|
||||
- Audit-Export für Compliance → M152
|
||||
|
||||
## Erfolgskriterium
|
||||
Test-Modul ruft `kontakt.create({...})` → ohne expliziten Audit-Code-Aufruf erscheint ein Eintrag in `audit_events` mit korrektem actor, tenant, before/after, timestamp.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Schema-Design separat von Hook-Implementierung
|
||||
- Akteur-Resolution unterscheidet User / Auto / Sync / System
|
||||
- Performance: Bulk-Update von 1000 Datensätzen darf nicht > 2x normale Latenz erzeugen
|
||||
- Audit-Writes sind unveränderlich (keine UPDATE/DELETE-Pfade)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,90 @@
|
||||
# M002 — Klartext-Diagnostik
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 1 (Bauprinzipien)
|
||||
**Bauprinzip:** A.1 — Klartext-Diagnostik in jedem Feature
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/03-architektur.md` Sektion A.1
|
||||
|
||||
## Ziel
|
||||
Jeder erkennbare Fehler-Zustand in HiveGrid hat einen vorformulierten Klartext-Text und (wo sinnvoll) einen Lösungs-Knopf — kein nackter HTTP-Code, kein kryptisches Log.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.1.1 — Fester Klartext-Text + optional Lösungs-Knopf pro Fehler-Zustand
|
||||
- A.1.2 — Keine KI-on-the-fly-Übersetzung in Phase 1; Texte sind redaktionell vorgefertigt
|
||||
- A.1.3 — Kein Feature-Release ohne definierte Klartext-Texte
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Wird benötigt von:** allen folgenden Modulen
|
||||
- **Hängt zusammen mit:** M003 (i18n), weil Klartext mehrsprach-fähig sein muss
|
||||
|
||||
## Out of Scope
|
||||
- KI-Live-Übersetzung von Fehlern (Phase 2)
|
||||
- Auto-Generierung von Texten
|
||||
|
||||
## Erfolgskriterium
|
||||
Geworfener Catalog-Fehler erscheint als deutscher Klartext-Hinweis im UI mit korrektem Lösungs-Knopf-Verhalten; ESLint-Rule lehnt nackte `throw new Error("...")` außerhalb des Catalogs ab.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Catalog-Format als TypeScript-Modul + i18n-Keys
|
||||
- Error-Boundary (RR7-kompatibel)
|
||||
- Logger-Bridge zu Pino
|
||||
- Migrations-Lint für bestehende Boilerplate-Fehler
|
||||
- Klartext-Beispiele aus Pflichtenheft-Modulen übernehmen (z.B. M27.15)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,89 @@
|
||||
# M003 — i18n-Pflicht-Wiring
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 1 (Bauprinzipien)
|
||||
**Bauprinzip:** A.4 — Mehrsprachigkeit von Anfang an sauber vorbereitet
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/03-architektur.md` Sektion A.4
|
||||
|
||||
## Ziel
|
||||
Kein einziger UI-Text wird hartkodiert. Build schlägt fehl, wenn ein nicht-erlaubter harter Text gefunden wird.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.4.1 — Alle Texte aus Sprach-Dateien (Locale-Files), keine Hardcoding
|
||||
- A.4.2 — DE Phase 1 befüllt; EN/TR/PL als Ziel-Sprachen vorbereitet, nicht befüllt
|
||||
- A.4.3 — Sprach-Wechsel pro Nutzer (siehe M028, M029)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Wird benötigt von:** allen folgenden Modulen mit UI
|
||||
- **Verwendet:** Boilerplate-`packages/i18n` (i18next + remix-i18next)
|
||||
|
||||
## Out of Scope
|
||||
- DeepL-Pipeline für DE → EN/TR/PL (Phase 2)
|
||||
- Sprach-Pflege-UI für Mandanten (gibt es nicht — Mandanten-Inhalte sind 1-sprachig)
|
||||
|
||||
## Erfolgskriterium
|
||||
Hartcodierter String im UI-Code (`packages/ui-hivegrid/**`) → Build schlägt fehl mit Klartext-Verstoß-Meldung. Pluralisierung (DE-Form) und Datums/Zahlen-Format funktionieren.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- i18next-Setup als Querschnitt-Service, einzig DE als Quelle
|
||||
- ESLint-Rule gegen JSX-Text-Nodes ohne `t()`
|
||||
- CI-Wiring (`pnpm verify:i18n` im baseline)
|
||||
- Pluralisierung: ICU MessageFormat (Polnisch hat 3 Formen — Phase 2 nicht brechen)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,87 @@
|
||||
# M004 — Tenant-Scope-Wrapper + Owner-Check
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 1 (Bauprinzipien)
|
||||
**Bauprinzip:** A.5 Teil 1 — Berechtigungs-Logik als Standard
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/03-architektur.md` Sektion A.5
|
||||
|
||||
## Ziel
|
||||
Jede Liste, Suche, Detail-Ansicht filtert automatisch nach Mandant + Berechtigungen. Owner-Check für „eigene Daten" zentral implementiert.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.5.1 — Auto-Filter nach angemeldetem Nutzer; ohne Recht: nicht im Menü, nicht aufrufbar, nicht in Suche
|
||||
- A.5.2 — Owner-Check zentral, nicht pro Modul nachgebaut
|
||||
- A.5.3 — Keine versteckten URL-Tricks zum Umgehen
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001 (Permission-Verstöße werden geauditet)
|
||||
- **Wird benötigt von:** allen Modulen, die Daten anzeigen
|
||||
|
||||
## Out of Scope
|
||||
- URL-Tampering-Probes + Mass-Action-Hardening → M005
|
||||
|
||||
## Erfolgskriterium
|
||||
Test-Modul vergisst den Filter → Wrapper greift trotzdem; Cross-Tenant-ID-Lookup liefert 404 (nicht 403).
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Wrapper für Prisma-Queries (`withTenantScope`, `withPermission`, `withOwnerCheck`)
|
||||
- Permission-Definition als Feingranular (siehe M27.6.2 — Stufen pro Funktionsbereich)
|
||||
- Test-Suite mit Cross-Tenant-Probe + Negative-Path
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,87 @@
|
||||
# M005 — URL-Tampering Hardening + Mass-Action-Schutz
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 1 (Bauprinzipien)
|
||||
**Bauprinzip:** A.5 Teil 2
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/03-architektur.md` Sektion A.5.3 + 27.2
|
||||
|
||||
## Ziel
|
||||
URL-Manipulation, Bulk-Operationen, kreative Query-Strings können Mandanten-Trennung nicht umgehen.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.5.3 — Keine versteckten URL-Tricks
|
||||
- 27.2.1 — System verhindert durchgehend Cross-Tenant-Datenzugriff
|
||||
- 27.2.3 — Auch Hintergrund-Prozesse setzen Mandanten-Bezug explizit
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M004 (Wrapper steht)
|
||||
- **Wird benötigt von:** allen Modulen mit ID-basierten Routen
|
||||
|
||||
## Out of Scope
|
||||
- Cache/CDN-Layer Probes (separat falls relevant)
|
||||
|
||||
## Erfolgskriterium
|
||||
Pen-Test-Suite mit URL-Tampering-Probes (fremde IDs, Cross-Tenant-Slug, Mass-DELETE-Versuche) liefert konsistent 404; Audit-Log erfasst alle Probe-Versuche.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Probe-Test-Suite als CI-Pflicht (Playwright)
|
||||
- Mass-Action-Validation (Bulk-Updates müssen IDs einzeln gegen Tenant prüfen)
|
||||
- Background-Job-Wrapper (BullMQ-Jobs setzen Tenant explizit)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,90 @@
|
||||
# M006 — Feature-Flag-Engine (Code-Layer)
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 1 (Bauprinzipien)
|
||||
**Bauprinzip:** A.7 — Feature-Flags als Standard-Einführungs-Hülle
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/03-architektur.md` Sektion A.7 + Modul 32
|
||||
|
||||
## Ziel
|
||||
Flag-Auswertung mit korrekter Priorität (direkte Ausnahme → Filter → Default). Code-Layer steht; Admin-UI später (M031-M033).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.7.1 — Neue Features hinter Flag, intern → ausgewählte → breit
|
||||
- A.7.2 — Plattform-Admin schaltet ohne Deploy
|
||||
- 32.4 — Auswertungs-Reihenfolge
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001 (Flag-Änderungen werden geauditet)
|
||||
- **Wird benötigt von:** allen folgenden Modulen mit gestaffeltem Roll-out
|
||||
|
||||
## Out of Scope
|
||||
- Admin-UI für Flag-Verwaltung → M031-M033
|
||||
- Mandanten-Selbstbedienungs-Flags (Phase 2)
|
||||
- Prozentualer Roll-out (Phase 2)
|
||||
- A/B-/C-Tests (Phase 2)
|
||||
|
||||
## Erfolgskriterium
|
||||
`featureFlag('foo', tenant)` returns korrekten Wert nach Priorität; Test-Mode mit forced overrides; im Code referenzierter aber nicht definierter Flag → Klartext-Build-Warnung.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Flag-Schema mit Lifecycle (Beta/Roll-out/GA/Abgekündigt)
|
||||
- Resolver mit Caching
|
||||
- Test-Mode für CI (forced overrides)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,86 @@
|
||||
# M007 — Idempotenz-Wrapper für BullMQ-Steps
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 1 (Bauprinzipien)
|
||||
**Bauprinzip:** A.8 — Idempotenz pro Automatisierungs-Aktion
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/03-architektur.md` Sektion A.8
|
||||
|
||||
## Ziel
|
||||
Jeder BullMQ-Step hat einen Idempotenz-Schlüssel; bei Re-Run wird die Aktion nicht doppelt ausgeführt.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.8.1 — Idempotenz-Schlüssel pro Step
|
||||
- A.8.2 — Konkret: keine doppelten Mails, Datensätze, KWP-Push-Operationen
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001 (Idempotenz-Skip wird geauditet), M004
|
||||
- **Wird benötigt von:** M075-M082 (Automation), M089-M095 (KWP-Sync), Mail-/Notification-Worker
|
||||
|
||||
## Out of Scope
|
||||
- Distributed-Lock-Service (BullMQ atomic ops reichen)
|
||||
|
||||
## Erfolgskriterium
|
||||
Job zweimal mit gleichem Key gequeued → läuft einmal, zweite Ausführung schreibt Audit-Skip-Eintrag.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Idempotency-Key-Store mit TTL
|
||||
- BullMQ-Wrapper als Higher-Order-Function
|
||||
- Replay-Tests mit Job-Crash-Szenarien
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,90 @@
|
||||
# M008 — Apps-Engine: Adapter-Interface + State-Machine
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 1 (Bauprinzipien)
|
||||
**Bauprinzip:** A.2 Teil 1 — Adapter-Schicht für jede Integration
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/03-architektur.md` A.2 + Modul 33a (Block 4)
|
||||
|
||||
## Ziel
|
||||
Abstrakte Adapter-Klasse + 5-Status-State-Machine (wartet/aktiv/eingeschränkt/defekt/getrennt). Eine Dummy-App zum Beweis.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.2.1 — Externe Systeme nur über Apps-Engine
|
||||
- A.2.2 — Adapter-Interface so gebaut, dass weitere Implementierungen ohne Engine-Umbau dazu kommen
|
||||
- 33a.3 — 5-Status mit Klartext-Hinweis pro Status
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M002, M001
|
||||
- **Wird benötigt von:** M009, M010 (Apps-Engine), alle Module mit externer Integration (M19, M9, M12, M25, M125, M131, M153)
|
||||
|
||||
## Out of Scope
|
||||
- Konkrete Adapter (KWP, Gmail, AirCall, Stripe, PandaDoc, Calendar) — eigene Module
|
||||
- Setup-Wizard → M009
|
||||
- Probe-Scheduler → M010
|
||||
- Drittanbieter-Marketplace (Phase 2)
|
||||
|
||||
## Erfolgskriterium
|
||||
Dummy-App durchläuft Lifecycle (wartet → aktiv → eingeschränkt → defekt → getrennt), Klartext-Hinweis pro Übergang sichtbar im Test-UI.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Adapter-Interface als TypeScript-Interface mit klaren Hooks (connect, probe, sync, disconnect)
|
||||
- State-Machine als XState oder einfache Enum-Transitions mit Audit-Eintrag pro Wechsel
|
||||
- Dummy-App als Referenz-Implementation
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,88 @@
|
||||
# M009 — Apps-Engine: Setup-Wizard + Sync-Log
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 1 (Bauprinzipien)
|
||||
**Bauprinzip:** A.2 Teil 2
|
||||
**Pflichtenheft-Quelle:** Modul 33a Sektionen 33a.2, 33a.4, 33a.7
|
||||
|
||||
## Ziel
|
||||
Generischer Setup-Wizard pro Anbindungs-Art (OAuth, API-Key, Username/PW, Local-Sync-Programm). Sync-Verlauf als Liste mit Klartext-Zusammenfassung pro Vorgang.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 33a.2 — Setup-Wizard-Reihenfolge: Voraussetzungs-Check → Zugangsdaten → Probe → optional Initial-Sync
|
||||
- 33a.4 — Vier Sync-Arten (Pull, Push, Webhook, manuell), Verlauf mit Filter
|
||||
- 33a.7 — Verwaltungs-Bereich „Integrationen" mit Re-Sync, Token-Refresh, Trennen
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M008, M013-M015 (UI-Layer)
|
||||
- **Wird benötigt von:** alle konkreten Adapter
|
||||
|
||||
## Out of Scope
|
||||
- Probe-Scheduler + Webhook-Schutz → M010
|
||||
- Konkrete Adapter
|
||||
|
||||
## Erfolgskriterium
|
||||
Dummy-App via Wizard verbinden in <60 Sek; Sync-Verlauf zeigt 5 letzte Vorgänge mit Klartext (z.B. „Sync mit X, 14 Datensätze gepullt, 2 fehlgeschlagen").
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Wizard-Form-Generator aus Adapter-Definition
|
||||
- Sync-Log mit Filter (Status/Operation/Datum) + Detail-Schublade
|
||||
- Connect/Disconnect mit Mehrfach-Bestätigung + Audit
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
+91
@@ -0,0 +1,91 @@
|
||||
# M010 — Apps-Engine: Probe-Scheduler + Webhook-Sturm-Schutz
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 1 (Bauprinzipien)
|
||||
**Bauprinzip:** A.2 Teil 3 + A.16 — Rate-Limit + Anomalie-Erkennung
|
||||
**Pflichtenheft-Quelle:** Modul 33a Sektionen 33a.3, 33a.5, 33a.6 + A.16
|
||||
|
||||
## Ziel
|
||||
Auto-Probe alle 5/15/30 Min je nach Status. Hard-Limit für Webhook-Events pro Stunde. Anomalie-Erkennung pausiert bei 10x normalem Volumen.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 33a.3.4 — Probe-Frequenz pro Status (aktiv: 5min, eingeschränkt: 1min, defekt: 15min)
|
||||
- 33a.5 — Webhook-Sturm-Schutz + Anomalie-Erkennung
|
||||
- 33a.6 — Schema-Drift-Schutz (für Apps allgemein, KWP-spezifisch in M092)
|
||||
- A.16.1 — Hartes Limit pro Mandant (Standard 1000 Trigger/h)
|
||||
- A.16.2 — Anomalie-Erkennung mit 10x-Schwelle
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M008, M009, M011 (Notifications)
|
||||
- **Wird benötigt von:** alle Adapter, M075-M082 (Automation)
|
||||
|
||||
## Out of Scope
|
||||
- Konkrete Adapter
|
||||
- Schema-Drift-Sentinel KWP-spezifisch → M092
|
||||
|
||||
## Erfolgskriterium
|
||||
Test-App bei 1500 Webhook-Events/h → 500 verworfen mit Klartext-Notification; bei 10x normalem Volumen pausiert Anomalie-Erkennung mit Klartext-Hinweis.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Probe-Scheduler als BullMQ-Cron mit Status-Adaption
|
||||
- Webhook-Receiver mit Rate-Limit pro Mandant + pro Endpoint
|
||||
- Anomalie-Detector als Rolling-Window-Average + Threshold
|
||||
- Klartext-Texte aus Pflichtenheft 33a.10 + Modul 17.8 übernehmen
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,88 @@
|
||||
# M011 — Notification-Service-Layer
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 1 (Bauprinzipien)
|
||||
**Bauprinzip:** — (Service-Layer für M22 Notifications-Modul)
|
||||
**Pflichtenheft-Quelle:** Modul 22 (Block 5)
|
||||
|
||||
## Ziel
|
||||
Service-API für In-App, Email, Push als Querschnitt — jeder Modul-Code ruft `notify({channel, recipient, template, payload})`. UI/Settings/Kategorien später (M115-M117).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- Modul 22 als Pflicht-Service für viele Module (Lead-Routing, Mandanten-Lifecycle, Apps-Engine-Status, Automation)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001, M002 (Klartext-Templates), M003 (i18n)
|
||||
- **Wird benötigt von:** ~30+ Modulen
|
||||
|
||||
## Out of Scope
|
||||
- Notification-Center-UI → M115
|
||||
- User-Settings (Kanäle, Stille Stunden) → M116
|
||||
- Kategorien + Bündelung → M117
|
||||
|
||||
## Erfolgskriterium
|
||||
Test-Modul ruft `notify({channel: 'push', recipient: userId, template: 'lead_received', payload: {...}})` → Push-Mock erhält korrekt formatierte Nachricht (DE-Klartext).
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Service-Interface + Channel-Adapter (In-App, Email via packages/mail, Push via Capacitor/FCM)
|
||||
- Template-Registry mit i18n-Keys
|
||||
- Idempotenz pro Notification (verwendet M007)
|
||||
- BullMQ-Queue für asynchronen Versand
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,91 @@
|
||||
# M012 — Workspace-Topologie
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 2 (UI-Hot-Swap-Architektur)
|
||||
**Architektur-Entscheidung:** Layer-Trennung lint-erzwungen
|
||||
|
||||
## Ziel
|
||||
Drei neue pnpm-Workspaces: `packages/view-models`, `packages/ui-hivegrid`, `packages/ui-subframe`. ESLint-Boundary-Rules verhindern Cross-Layer-Imports.
|
||||
|
||||
## Architektur-Bezug
|
||||
Aus Party-Mode-Diskussion (Sally + Winston + Amelia, 2026-05-10):
|
||||
- `app/routes/**` → Loaders/Actions, baut View-Models, importiert `packages/ui-hivegrid`
|
||||
- `app/domain/**` → Domain-Logik, Prisma, BullMQ — KEIN React, KEIN UI
|
||||
- `packages/view-models/**` → pure Funktionen (domain → VM); KEIN React, KEIN Prisma
|
||||
- `packages/ui-hivegrid/**` → Library-Adapter; KEIN Prisma, KEIN Auth
|
||||
- `packages/ui-subframe/**` → Subframe-Output unangefasst; NIE direkt von Routes importiert
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** EU-Sterilisation + RR7-Migration der Boilerplate
|
||||
- **Wird benötigt von:** M013-M017, alle Module mit UI
|
||||
|
||||
## Out of Scope
|
||||
- View-Model-Konvention (Naming, Schemas) → M013
|
||||
- Subframe-Adapter-Layer → M015
|
||||
|
||||
## Erfolgskriterium
|
||||
`pnpm typecheck` grün; ESLint blockiert Import von `~/db` in `packages/ui-hivegrid/**` als Build-Fehler.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- pnpm-workspace.yaml Anpassung
|
||||
- TypeScript Project-References zwischen den Paketen
|
||||
- ESLint-Boundary-Plugin (`eslint-plugin-import-boundaries` oder Custom-Rules)
|
||||
- Skeleton-Files in jedem Paket damit der Workspace direkt baut
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
# M013 — View-Model-Konvention
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 2 (UI-Hot-Swap-Architektur)
|
||||
**Architektur-Entscheidung:** Synchron im Loader, Zod-validiert
|
||||
|
||||
## Ziel
|
||||
Naming-Pattern für View-Models, Discriminated-Unions für Loading/Error, Zod-Schema pro VM, ESLint-Rule gegen React-Imports im VM-Paket.
|
||||
|
||||
## Architektur-Bezug
|
||||
Server bereitet VM einmal vor (synchron im Loader), UI rendert nur — kein client-seitiges Re-Compute.
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M012
|
||||
- **Wird benötigt von:** M014, M015, alle Module mit UI
|
||||
|
||||
## Out of Scope
|
||||
- Action-Callbacks → M014
|
||||
|
||||
## Erfolgskriterium
|
||||
Beispiel-VM (`KontaktDetailVM`) durchläuft kompletten Pfad: Loader baut, Zod validiert, UI rendert; React-Import in `packages/view-models/**` → Build-Fehler.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Naming-Konvention: `<Domain><Use>VM` (z.B. `KontaktListVM`, `KontaktDetailVM`)
|
||||
- Discriminated-Union für Loading/Error/Success (`{state: 'loaded', data: ...}`)
|
||||
- Zod-Schema neben Type für Runtime-Validierung
|
||||
- Pure Functions: `toKontaktDetailVM(entity, ctx) → KontaktDetailVM`
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# M014 — Action-Callback-Contract
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 2 (UI-Hot-Swap-Architektur)
|
||||
**Architektur-Entscheidung:** Components erhalten Actions als Callback-Props, kein RR7-Hook intern
|
||||
|
||||
## Ziel
|
||||
Standard-Shape `{ onX: (input) => Promise<Result> | void }` für alle UI-Aktionen. UI-Components rufen Hooks wie `useFetcher` NIE selbst auf — Routes injizieren die Callbacks.
|
||||
|
||||
## Architektur-Bezug
|
||||
Aus den drei Anti-Patterns: kein `useLoaderData`/`useFetcher` in `packages/ui-hivegrid/**`.
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M012, M013
|
||||
- **Wird benötigt von:** alle interaktiven UI-Components
|
||||
|
||||
## Out of Scope
|
||||
- Konkrete Modul-Actions (jedes Modul definiert eigene)
|
||||
|
||||
## Erfolgskriterium
|
||||
Beispiel: `KontaktDetailPage` empfängt `actions={{onEdit, onArchive}}` als Prop. Test mit `vi.fn()`-Spies bestätigt Callback-Shape; ESLint blockiert `useFetcher` in `packages/ui-hivegrid/**`.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Callback-Type-Pattern als Conventions-Doku
|
||||
- Test-Helper für Action-Spy-Setup
|
||||
- Migrations-Lint (alte Boilerplate-Fetcher-Nutzung in UI flagged)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# M015 — Subframe-Adapter-Layer
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 2 (UI-Hot-Swap-Architektur)
|
||||
**Architektur-Entscheidung:** Brücke `packages/ui-subframe` → `packages/ui-hivegrid`
|
||||
|
||||
## Ziel
|
||||
Mapping-Komponenten in `packages/ui-hivegrid/src/adapters/*` binden Subframe-Primitives an View-Model-Slots. Subframe-Output bleibt unangetastet, Adapter macht die Übersetzung.
|
||||
|
||||
## Architektur-Bezug
|
||||
Designer baut in Subframe, exportiert Code, AI-Agent integriert. Adapter ist die Schnittstelle.
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M012-M014
|
||||
- **Wird benötigt von:** alle Module mit UI
|
||||
|
||||
## Out of Scope
|
||||
- Konkrete Modul-Pages (jedes Modul nutzt das Pattern)
|
||||
|
||||
## Erfolgskriterium
|
||||
Beispiel-Adapter: Subframe-Komponente `<DataTable>` wird via Adapter zu HiveGrid-`<KontaktList vm={...} actions={...}>` — Replace der Subframe-Komponente erfordert nur Adapter-Update, nicht Routes.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Adapter-Pattern als Type-Bridge (Subframe-Props ↔ HiveGrid-VM)
|
||||
- AI-Agent-Briefing in `AGENTS.md` mit Adapter-Beispielen
|
||||
- Test: Adapter-Snapshot pro Subframe-Component
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
# M016 — Visual-Regression-Gate
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 2 (UI-Hot-Swap-Architektur)
|
||||
**Architektur-Entscheidung:** Playwright Screenshot-Diff in CI (kein separates Storybook)
|
||||
|
||||
## Ziel
|
||||
Vor jedem Merge fotografiert Playwright alle Kern-Pages mit Fixture-VMs und vergleicht mit Baseline. Diff > Threshold → CI bricht mit Klartext-Liste der betroffenen Screens.
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M012-M015
|
||||
- **Wird benötigt von:** alle Module mit UI (laufendes Gate)
|
||||
|
||||
## Out of Scope
|
||||
- E2E-Flow-Tests mit Login (separat)
|
||||
- Storybook-Build (entfällt — Subframe ist Catalog)
|
||||
|
||||
## Erfolgskriterium
|
||||
Trivialer Style-Change in `packages/ui-subframe` → CI listet 23 betroffene Pages mit Diff-Bildern. Bewusster Update → Approve-Workflow setzt neue Baseline.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Playwright Component-Testing-Setup
|
||||
- Fixture-VM-Repository in `packages/view-models/**/__fixtures__/*.ts`
|
||||
- CI-Pipeline mit Diff-Artefakt-Upload (für PR-Review)
|
||||
- Threshold-Konfiguration (Pixel-Diff-Tolerance)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M017 — Hot-Swap-Drill
|
||||
|
||||
**Block:** Querschnitt-Hülle Teil 2 (UI-Hot-Swap-Architektur)
|
||||
**Architektur-Entscheidung:** Synthetischer UI-Lib-Tausch in CI
|
||||
|
||||
## Ziel
|
||||
CI-Job tauscht `packages/ui-hivegrid` gegen `packages/ui-mock` (Minimal-Komponenten ohne Styles), führt Smoke-E2E aus. Wenn die App noch funktioniert (Routen laden, Actions feuern, Loader liefern Daten), ist Hot-Swap real.
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M012-M016
|
||||
- **Wird benötigt von:** Sicherheitsnetz für M015 + alle UI-Module
|
||||
|
||||
## Out of Scope
|
||||
- Visuelle Regression (separat in M016)
|
||||
|
||||
## Erfolgskriterium
|
||||
`packages/ui-mock` als Drop-in-Replacement: Smoke-E2E grün ohne Code-Änderung außerhalb von `packages/ui-mock`. Versteckte Kopplung in irgendeinem Modul → Drill bricht mit konkreter Datei-Referenz.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- `packages/ui-mock` als Skelett-Lib mit gleicher Component-Signatur, aber `<div>{children}</div>`-Implementations
|
||||
- CI-Job-Variante: `pnpm test:hot-swap`
|
||||
- Smoke-E2E-Suite als Pflicht-Pfad pro Route
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,93 @@
|
||||
# M018 — Mandanten-Anlage
|
||||
|
||||
**Block:** Block 1 — Plattform-Fundament · Modul 27 (Anmeldung/Mandanten/Rollen)
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/blocks/block1.md` Abschnitt 27.1
|
||||
|
||||
## Ziel
|
||||
Eine Handwerksfirma kann sich selbst als neuer Mandant registrieren oder wird manuell durch Plattform-Admin angelegt. Eindeutiger Slug, Branche, AGB/AVV-Zustimmung.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 27.1.1 — Zwei Wege: Self-Service oder manuell durch HiveGrid
|
||||
- 27.1.2 — Pflichtangaben: Email, Passwort, Firmenname, Vor-/Nachname, Branche, Firmengröße, AGB/Datenschutz/AVV
|
||||
- 27.1.3 — Optional: Telefon, USt-IdNr.
|
||||
- 27.1.4 — Slug auto-generiert, vom User änderbar
|
||||
- 27.1.5 — Live-Eindeutigkeitsprüfung mit Vorschlag bei Konflikt
|
||||
- 27.1.6 — Slug nach Anlage nicht änderbar (außer durch HiveGrid-Support)
|
||||
- 27.1.7 — Phase 1: nur SHK aktiv, andere als „Demnächst"
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001 (Audit), M002 (Klartext), M003 (i18n), M012-M015 (UI-Layer)
|
||||
- **Wird benötigt von:** M019, M020, M026, M157 (Onboarding), M036 (Plattform-Admin)
|
||||
|
||||
## Out of Scope
|
||||
- Massen-Einladung CSV (Phase 2)
|
||||
- Eigene Domain pro Mandant (Phase 2, Enterprise)
|
||||
- Konkrete Daten-Provisionierung → M158
|
||||
|
||||
## Erfolgskriterium
|
||||
Self-Service-Anmeldung: Geerkens-Test-Mandant in <3 Min angelegt, Slug eindeutig, AGB-Zustimmung dokumentiert, Bestätigungs-Email versendet.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Slug-Generator + Live-Uniqueness-Probe
|
||||
- Branche-Whitelist (Phase 1: nur SHK aktiv)
|
||||
- AGB/AVV-Versionierung (siehe M37.16.2)
|
||||
- Audit-Log-Eintrag pro Mandanten-Anlage
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,89 @@
|
||||
# M019 — Mandanten-Trennung Hardening
|
||||
|
||||
**Block:** Block 1 · Modul 27
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 27.2
|
||||
|
||||
## Ziel
|
||||
Strikte Mandanten-Trennung durchgesetzt — keine Cross-Tenant-Sichtbarkeit, auch nicht in Hintergrund-Jobs, nicht über URL-Manipulation, nicht in zwischengespeicherten Daten oder Dateien.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 27.2.1 — Durchgehende Verhinderung Cross-Tenant Lese/Schreib/Löschen
|
||||
- 27.2.2 — Trennung gilt für Dateien + Cache
|
||||
- 27.2.3 — Hintergrund-Prozesse setzen Mandanten-Bezug explizit
|
||||
- 27.2.4 — Mehrfach-Mandanten-Mitgliedschaft + Wechsel-Funktion
|
||||
- 27.2.5 — Mandanten-Auswahl beim Login
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001, M004, M005, M018
|
||||
- **Wird benötigt von:** ALLE folgenden Module
|
||||
|
||||
## Out of Scope
|
||||
- URL-Tampering-Probes generisch → M005
|
||||
|
||||
## Erfolgskriterium
|
||||
Pen-Test-Suite mit Cross-Tenant-Probes (Cache-Spillover, BullMQ-Job ohne Tenant, Datei-Cross-Read) liefert konsistent 404 oder Klartext-Block; Mandanten-Wechsel-UI durchgehend erreichbar.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- BullMQ-Job-Wrapper: jeder Job MUSS tenant_id im Payload haben
|
||||
- Cache-Keys mit tenant_id präfixiert
|
||||
- Datei-Storage Bucket-Strategie (Scaleway S3 Pro-Tenant-Pfad)
|
||||
- Mandanten-Switcher in der App-Shell
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,90 @@
|
||||
# M020 — Email/Passwort-Auth + HIBP + Brute-Force
|
||||
|
||||
**Block:** Block 1 · Modul 27
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 27.3
|
||||
|
||||
## Ziel
|
||||
Standard-Login per Email+Passwort. Mindestens 12 Zeichen, HIBP-Leak-Check, Brute-Force-Schutz, 3+-Versuche → Captcha, 5/15-Min Account-Lock.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 27.3.1 — Email + Passwort als Standard
|
||||
- 27.3.2 — ≥12 Zeichen, keine Sonderzeichen-Zwang, HIBP-Check mit Klartext-Hinweis
|
||||
- 27.3.5 — 5/15-Min Account-Lock, Captcha ab 3. Fehlversuch
|
||||
- 27.3.6 — Passwort-Reset beendet alle Sessions
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M002 (Klartext), M003 (i18n), M001 (Audit), M018, EU-Sterilisation (TOTP/Magic-Link statt remix-auth-google)
|
||||
- **Wird benötigt von:** M021, M022, alle Module mit Auth-Pflicht
|
||||
|
||||
## Out of Scope
|
||||
- Magic-Link → M021
|
||||
- TOTP → M022
|
||||
- Microsoft-Anmeldung (Phase 2)
|
||||
- Apple/Google-Login (Anti-Liste)
|
||||
|
||||
## Erfolgskriterium
|
||||
Login mit korrektem PW grün, mit falschem PW Klartext-Hinweis + Counter, nach 5 Fehl-Versuchen 15-Min-Lock; HIBP-API-Probe blockiert geleaktes Passwort beim Setzen.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- HIBP via k-Anonymity-API (`https://api.pwnedpasswords.com/range/`)
|
||||
- Captcha-Integration (Google reCAPTCHA Phase 2 prüfen — alternativ hCaptcha EU)
|
||||
- Klartext-Texte aus Pflichtenheft 27.15
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,88 @@
|
||||
# M021 — Magic-Link + Sitzungs-Verwaltung
|
||||
|
||||
**Block:** Block 1 · Modul 27
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitte 27.3.3, 27.5
|
||||
|
||||
## Ziel
|
||||
Magic-Link als alternativer Login (15 Min, einmal nutzbar). Session-Mgmt: 30 Tage default, 4h-Inaktivitäts-Refresh, sichtbare aktive Sessions mit Beend-Funktion.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 27.3.3 — Magic-Link 15 Min gültig, single-use
|
||||
- 27.5.1 — 30-Tage Sliding-Session, Admin-konfigurierbar
|
||||
- 27.5.2 — 4h-Inaktivitäts-Soft-Refresh
|
||||
- 27.5.3 — Sichtbare aktive Sessions: Gerät, Browser, Standort, letzte Aktivität, Beenden
|
||||
- 27.5.4 — Auto-Beendigung bei PW/Email/2FA/Deaktivierung
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M020, M011 (Notifications für Email-Versand)
|
||||
- **Wird benötigt von:** M022, M026
|
||||
|
||||
## Out of Scope
|
||||
- TOTP → M022
|
||||
|
||||
## Erfolgskriterium
|
||||
Magic-Link-Email zugestellt, Klick loggt ein, zweiter Klick liefert Klartext „bereits genutzt"; Session-Liste zeigt aktive Geräte; Session-Beenden funktioniert sofort.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Single-use Token mit DB-Lookup (kein JWT-only)
|
||||
- Session-Liste mit Geo-IP-Lookup (lokal, nicht SaaS) für Standort
|
||||
- Klartext aus 27.15.3
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,89 @@
|
||||
# M022 — TOTP-2FA + Notfall-Codes
|
||||
|
||||
**Block:** Block 1 · Modul 27
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 27.4
|
||||
|
||||
## Ziel
|
||||
TOTP-Authenticator-App als zweiter Faktor (kein SMS). 10 Notfall-Codes, „Gerät 30 Tage merken"-Option mit Widerruf. Pflicht für Admins, optional für Mitarbeiter; Admin kann mandantenweit Pflicht aktivieren.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 27.4.1 — Nur Authenticator-App, keine SMS
|
||||
- 27.4.2 — 10 einmalige Notfall-Codes
|
||||
- 27.4.3 — Pflicht für Mandanten-Admin, optional für andere; Mandanten-weit Pflicht möglich
|
||||
- 27.4.4 — „30 Tage merken" pro Gerät, einzeln widerrufbar
|
||||
- 27.4.5 — 2FA-Reset durch Mandanten-Admin (mit Audit) bzw. HiveGrid-Support
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M020, M021
|
||||
- **Wird benötigt von:** M026 (Lifecycle), M034 (Plattform-Admin-Auth)
|
||||
|
||||
## Out of Scope
|
||||
- Hardware-Keys (FIDO2/WebAuthn) — Phase 2
|
||||
- SMS — explizit ausgeschlossen
|
||||
|
||||
## Erfolgskriterium
|
||||
TOTP-Setup mit QR-Code in <2 Min; Login mit korrektem Code grün; Notfall-Codes als Download/Druck; „30 Tage merken" persistiert; Admin-Reset im Audit-Log.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- `otpauth`-Library oder vergleichbare EU-neutrale TOTP-Lib
|
||||
- Notfall-Codes hashed in DB (bcrypt oder argon2)
|
||||
- QR-Code-Generierung clientside (qrcode.react bereits in Boilerplate)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,87 @@
|
||||
# M023 — Rollen-Engine + 6 SHK-Standard-Rollen + Gruppen
|
||||
|
||||
**Block:** Block 1 · Modul 27
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitte 27.6, 27.7, 27.8
|
||||
|
||||
## Ziel
|
||||
Rollen-Engine mit Stufen pro Funktionsbereich. Neuer SHK-Mandant erhält 6 Standard-Rollen [N1] (Partner-Liste 19.06.: Geschäftsführer, Projektleiter, Verwaltung, Vertriebler, Kundensupporter, Monteur). Gruppen für Filter ohne Rechte-Wirkung.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 27.6 — Rollen-Modell mit Stufen + Mehrfach-Rolle
|
||||
- 27.7 — 6 SHK-Standard-Rollen-Tabelle [N1, 09.05.2026]
|
||||
- 27.8 — Gruppen für Massen-Aktionen, Filter, Notifications
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M004 (Permission-Wrapper), M018 (Mandant)
|
||||
- **Wird benötigt von:** M024, alle folgenden Module mit Permission-Bedarf
|
||||
|
||||
## Out of Scope
|
||||
- Schalter pro einzelnem Nutzer (Phase 2)
|
||||
|
||||
## Erfolgskriterium
|
||||
Neuer SHK-Mandant: 10 Rollen automatisch angelegt, Mandanten-Admin kann Rollen umbenennen/anpassen; Gruppen-Anlage + Mitglieder-Zuordnung; Mehrfach-Rolle pro User addiert Rechte korrekt.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Permission-Definition als TypeScript-Konst + Stufen pro Bereich
|
||||
- Rollen-Templates als Konfigurations-Datei (Bauprinzip A.3)
|
||||
- UI für Rollen-Verwaltung in Mandanten-Admin
|
||||
- 27.6.6 (Büro-/Baustellen-Oberfläche-Default pro Rolle)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,88 @@
|
||||
# M024 — Mitarbeiter-Einladung / Deaktivierung / Umverteilung
|
||||
|
||||
**Block:** Block 1 · Modul 27
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 27.9
|
||||
|
||||
## Ziel
|
||||
Mandanten-Admin lädt Mitarbeiter per Email ein (7-Tage-Link), kann deaktivieren oder entfernen. Vor Entfernung Pflicht-Prüfung auf zugeordnete Aufgaben/Vertrieb/Projekte mit Massen-/Einzel-Umverteilungs-Funktion.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 27.9.1-27.9.3 — Einladungs-Flow
|
||||
- 27.9.4 — Deaktivieren (reversibel) vs. Entfernen (irreversibel)
|
||||
- 27.9.5 — Pflicht-Daten-Umverteilung vor Entfernung
|
||||
- 27.9.6 — Letzter Admin nicht entfernbar
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M020, M021, M023, M011 (Notifications)
|
||||
- **Wird benötigt von:** M025 (Lösch-Flow), M036 (Plattform-Admin)
|
||||
|
||||
## Out of Scope
|
||||
- Massen-Einladung CSV (Phase 2)
|
||||
- Microsoft-SSO (Phase 2)
|
||||
|
||||
## Erfolgskriterium
|
||||
Einladung verschickt + Link funktioniert; Mitarbeiter mit 12 offenen Aufgaben kann erst nach Umverteilung entfernt werden; Deaktivierung sofortige Session-Beendigung.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Einladungs-Token mit DB-Lookup, 7-Tage-TTL
|
||||
- Daten-Umverteilungs-UI mit Konflikt-Anzeige (27.15.6)
|
||||
- Bei bestehendem Account: direkter Mandanten-Beitritt
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,86 @@
|
||||
# M025 — Konto-Löschung (User + Admin)
|
||||
|
||||
**Block:** Block 1 · Modul 27
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 27.10 [N2, 09.05.2026]
|
||||
|
||||
## Ziel
|
||||
DSGVO- + Apple-konformer Lösch-Flow: mehrstufig (Erklärung, Identitäts-Bestätigung, Sonderfall-Prüfung, finale 3-Sek-Wartezeit). 24h Restore-Fenster. Admin-initiierte Löschung mit Audit + Email-Mitteilung.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 27.10.1-27.10.4 — User-Self-Lösch-Flow + 24h-Restore
|
||||
- 27.10.5 — Admin-Notification bei Self-Löschung [N2]
|
||||
- 27.10.6 — Admin-initiierte Löschung mit Pflicht-Begründung [N2]
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M020, M022, M001 (Audit), M011, M024 (Daten-Umverteilung)
|
||||
- **Wird benötigt von:** M164 (DSGVO-Export), M165 (Lösch-Workflow plattformweit)
|
||||
|
||||
## Out of Scope
|
||||
- Mandanten-Komplett-Löschung → M026
|
||||
|
||||
## Erfolgskriterium
|
||||
User-Self-Löschung: 4-Stufen-Flow erfolgreich, Daten anonymisiert (Name/Email/Avatar weg, „ehemaliger Mitarbeiter" in Verknüpfungen); Admin sieht Notification; Admin-Lösch-Flow gleicher Schutz.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Anonymisierungs-Strategie: identifizierende Felder weg, Verknüpfungen bleiben
|
||||
- 24h-Restore-Job (BullMQ delayed)
|
||||
- Sonderfall: einziger Admin → blockiert (27.10.2 + 27.15.7)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,89 @@
|
||||
# M026 — Mandanten-Lebenszyklus
|
||||
|
||||
**Block:** Block 1 · Modul 27
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 27.11
|
||||
|
||||
## Ziel
|
||||
Mandant durchläuft Zustände (Test, Bezahlend, Zahlung gescheitert, Pausiert, Gesperrt, Kündigung läuft, Gelöscht). Pro Zustand Klartext-Banner und nächste-Handlung. Read-only-Modus bei Zahlungs-Fail.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 27.11.1 — 7 Zustände
|
||||
- 27.11.2 — Zahlungs-Fail → Read-only nach 30 Tagen → Kündigung
|
||||
- 27.11.3 — Freiwillige Pausierung mit reduzierter Gebühr
|
||||
- 27.11.4 — 30-Tage-Karenz vor finaler Löschung
|
||||
- 27.11.5 — Klartext-Banner pro Zustand
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M002, M001, M153 (Stripe), M011 (Notifications)
|
||||
- **Wird benötigt von:** M155 (Trial), M036 (Plattform-Admin)
|
||||
|
||||
## Out of Scope
|
||||
- Stripe-Integration konkret → M153
|
||||
- Trial+Read-Only-Downgrade-Flow → M155
|
||||
|
||||
## Erfolgskriterium
|
||||
State-Machine durchläuft alle 7 Zustände in Test-Szenarien; Zahlungs-Fail simuliert → Read-only nach 30 Tagen + Klartext-Banner; freiwillige Pause + Reaktivierung funktionieren.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Lifecycle-State-Machine (XState oder einfache Enum)
|
||||
- Banner-Component mit Klartext-Text + Lösungs-Knopf pro State
|
||||
- Stripe-Webhook-Empfänger (delegiert an M153)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,86 @@
|
||||
# M027 — API-Keys + Tarif-Feature-Gates
|
||||
|
||||
**Block:** Block 1 · Modul 27
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitte 27.12, 27.13
|
||||
|
||||
## Ziel
|
||||
Mandanten-API-Keys mit Scope, 365-Tage-Rotation, Last-100-Requests-Log. Tarif-Feature-Gates: Funktion in tieferem Tarif → Klartext + Pricing-Link.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 27.12 — API-Keys (Name, Scope, Rotation, Rate-Limit, Last-100-Requests)
|
||||
- 27.13 — Tarif-Gates: Klartext + Link zu hivegrid.de/pricing (Apple-Compliance)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001 (Audit), M006 (Feature-Flag-Engine)
|
||||
- **Wird benötigt von:** M161-M163 (Public-API), M153 (Subscriptions)
|
||||
|
||||
## Out of Scope
|
||||
- OAuth2-für-Drittanbieter (Phase 2, Anti-Liste)
|
||||
- Schreibendes Public-API (Phase 2, Anti-Liste)
|
||||
|
||||
## Erfolgskriterium
|
||||
API-Key-Anlage einmal sichtbar (Sicherheits-Standard); Rate-Limit greift bei >1000 Req/h; Tarif-Gate führt auf Pricing-Link statt In-App-Checkout (Apple-Vorgabe).
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Hashed-Storage (nur Hash in DB, Plain einmal beim Anlegen)
|
||||
- Last-100-Requests-Ringbuffer pro Key
|
||||
- Pricing-Link in `t()` (kein Hardcoded-URL)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,88 @@
|
||||
# M028 — User/Tenant Sprach-Settings + Auflösungs-Reihenfolge
|
||||
|
||||
**Block:** Block 1 · Modul 30
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitte 30.1-30.3
|
||||
|
||||
## Ziel
|
||||
Pro-User Sprach-Setting + Mandanten-Default. Auflösungs-Reihenfolge: User > Mandant > Browser > DE. Outgoing: Empfänger-Sprache > Kontakt-Sprache > Mandanten-Default > DE. ICU-Pluralisierung.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 30.1.1-30.1.6 — Grundprinzip (kein Hardcoding, Ganzsatz-Übersetzung, ICU-Plural, Format-Lokalisierung)
|
||||
- 30.2 — User-/Mandant-/Kontakt-Sprache
|
||||
- 30.3 — Plattform-Text vs. Mandanten-Inhalte (1-sprachig in Phase 1)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M003 (i18n-Pflicht-Wiring)
|
||||
- **Wird benötigt von:** M029, M092 (Email-Versand), alle UI-Module
|
||||
|
||||
## Out of Scope
|
||||
- DeepL-Pipeline → Phase 2
|
||||
- Mehrsprachige Mandanten-Inhalte → Phase 2
|
||||
- Auto-Chat-Übersetzung → Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
DE-Mitarbeiter und (Phase-2-Mock) PL-Mitarbeiter im selben Mandanten sehen unterschiedliche UI-Sprachen; Email an Kontakt mit Sprach-Setting nutzt Empfänger-Sprache.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Resolver-Funktion `resolveLocale(user, tenant, browser, default)`
|
||||
- ICU-MessageFormat (i18next-icu-plugin)
|
||||
- Format-Helper für Datum/Zahl pro Locale
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
# M029 — Sprach-Wechsler + Fallback-Hinweise
|
||||
|
||||
**Block:** Block 1 · Modul 30
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitte 30.4, 30.6
|
||||
|
||||
## Ziel
|
||||
Sofortiger Sprach-Wechsel ohne Reload. Public-Pages (Hilfe, Booking, Forms) mit Cookie-merkendem Sprach-Wähler. Klartext-Hinweise bei unvollständig-befüllter Sprache.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 30.4.1 — Live-Wechsel ohne Reload
|
||||
- 30.4.2 — Cookie-merkender Wähler auf Public-Pages
|
||||
- 30.6 — Klartext bei Fallback (Sprache nicht vollständig befüllt)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M028, M015 (UI-Layer)
|
||||
- **Wird benötigt von:** alle UI-Module
|
||||
|
||||
## Out of Scope
|
||||
- Mehrsprachiges Hilfe-Center → Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
Sprach-Wechsel im Settings live wirksam; Public-Booking-Page mit Cookie-Persistenz; Test-Modul mit unvollständigem Locale → User sieht 30.6.1-Hinweis.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Locale-Switcher als reusable Component in `packages/ui-hivegrid`
|
||||
- Cookie-Strategy für Public-Pages (httpOnly: false, samesite: lax)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# M030 — Hell/Dunkel-Modus + Capacitor-Status-Bar
|
||||
|
||||
**Block:** Block 1 · Modul 31 (Phase 1)
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 31.1
|
||||
|
||||
## Ziel
|
||||
Pro-User „System / Hell / Dunkel" mit Live-Wechsel ohne Reload, kein Aufblitzen, Capacitor-Status-Bar respektiert Modus.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 31.1.1-31.1.6 — Drei Modi, System-Default, Live-Sync, No-Flash via Cookie, Capacitor-Status-Bar
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M015 (UI-Layer), M167 (Capacitor-Setup, dependency-soft — Mobile-Status-Bar erst mit M168)
|
||||
- **Wird benötigt von:** alle UI
|
||||
|
||||
## Out of Scope
|
||||
- Logo-Upload, Custom-Farben, White-Label → Phase 2 (siehe 31.2-31.4)
|
||||
|
||||
## Erfolgskriterium
|
||||
Mode-Switch live ohne Reload; Mac-Auto-Wechsel auf Dunkel zur Abendzeit greift in offener Session; iOS/Android-Splash respektiert Modus.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- `next-themes` bereits in Boilerplate-Deps
|
||||
- SSR-Cookie für No-Flash
|
||||
- Tailwind `dark:`-Variant einheitlich angewendet
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
# M031 — Feature-Flag Schalter-Definition + Lifecycle
|
||||
|
||||
**Block:** Block 1 · Modul 32
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitte 32.1, 32.2
|
||||
|
||||
## Ziel
|
||||
Plattform-Admin-UI: Schalter mit Lifecycle (Beta/Roll-out/GA/Abgekündigt), Verantwortlicher, Modul-Tag, Beschreibung, Standard-Wert.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 32.1 — Definition + Mandanten sehen keine Eigen-Verwaltung in Phase 1
|
||||
- 32.2 — Pflicht-Stammdaten + Lifecycle-Stufen
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M006 (Feature-Flag-Engine), M034 (Plattform-Admin-Auth)
|
||||
- **Wird benötigt von:** M032, M033
|
||||
|
||||
## Out of Scope
|
||||
- Filter/Ausnahme-Editoren → M032
|
||||
- Massen-/Statistik → M033
|
||||
|
||||
## Erfolgskriterium
|
||||
Plattform-Admin legt Schalter „beta-foo" an, sieht ihn in Liste mit Stufe „Beta"; Lifecycle-Wechsel mit Bestätigungs-Dialog.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Liste mit Filter (Stufe, Modul, Verantwortlicher)
|
||||
- Detail-Ansicht mit Verlauf
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,86 @@
|
||||
# M032 — Feature-Flag Filter-Editor + Einzel-Ausnahme-Editor
|
||||
|
||||
**Block:** Block 1 · Modul 32
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 32.3, 32.4, 32.5
|
||||
|
||||
## Ziel
|
||||
Filter-Editor mit Live-Vorschau („12 Mandanten betroffen"). Einzel-Ausnahme mit optionalem Ablaufdatum. Auswertungs-Reihenfolge sichtbar.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 32.3 — Drei Setz-Wege (Default, Filter, Ausnahme)
|
||||
- 32.4 — Auswertungs-Reihenfolge (Ausnahme > Filter > Default)
|
||||
- 32.5 — Verwaltungs-Oberfläche
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M031, M006
|
||||
- **Wird benötigt von:** M033
|
||||
|
||||
## Out of Scope
|
||||
- Prozentualer Roll-out → Phase 2
|
||||
- Zeitgesteuerte Aktivierung → Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
Filter „SHK-Mandanten >50 MA" → Live-Vorschau zeigt Treffer-Anzahl; Einzel-Ausnahme „Geerkens-Pilot" überstimmt Filter.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Filter-DSL als JSON mit Mandanten-Properties
|
||||
- Resolver-Test mit Edge-Cases (32.4)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
# M033 — Feature-Flag Massen-Funktionen + Statistik + Audit-Historie
|
||||
|
||||
**Block:** Block 1 · Modul 32
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitte 32.5.6-32.5.8, 32.7, 32.9
|
||||
|
||||
## Ziel
|
||||
Massen-Setzen für 12 Mandanten gleichzeitig. Wirkungs-Statistik („X aktiv, Y nicht"). Änderungs-Historie + Klartext-Hinweise (Filter wirkungslos, Ablaufdatum vergangen).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 32.5.6-32.5.8 — Massen + Lifecycle-Wechsel + Archiv
|
||||
- 32.7 — Audit-Protokoll
|
||||
- 32.9 — Klartext-Hinweise
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M032, M001 (Audit)
|
||||
- **Wird benötigt von:** Plattform-Admin-Workflow
|
||||
|
||||
## Out of Scope
|
||||
- Nutzungs-Telemetrie → Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
Massen-Aktivierung für 12 Mandanten in 1 Aktion; Statistik-Kachel zeigt Live-Trefferzahl; archivierter Schalter bleibt sichtbar mit „Archiv"-Tag.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Bulk-Action mit Confirmation + Audit
|
||||
- Klartext aus 32.9 übernehmen
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
# M034 — Plattform-Admin-Auth (admin.<domain>)
|
||||
|
||||
**Block:** Block 1 · Modul 37
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitte 37.1, 37.2
|
||||
|
||||
## Ziel
|
||||
Strikt getrennte Plattform-Admin-Welt auf eigener Subdomain (`admin.hivegrid.de`). Eigene Konten, eigene Sessions (8h, 1h Inaktivitäts-Timeout), 2FA Pflicht, IP-Wechsel löst Re-Auth aus.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 37.1 — Strikte Trennung (Subdomain, Cookies, kein Generalschlüssel)
|
||||
- 37.2 — Auth-Spezifika (kein Magic-Link, 2FA Pflicht, 5/15 Lock, 10/24h Konto-Sperre, IP-Wechsel = Re-Auth)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M020, M022, M001
|
||||
- **Wird benötigt von:** M035-M041
|
||||
|
||||
## Out of Scope
|
||||
- Hardware-Keys → Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
admin.hivegrid.de erreichbar, Cookies getrennt von app.hivegrid.de; 2FA-Pflicht beim Anlegen; IP-Wechsel mid-Session → Re-Auth-Prompt.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Subdomain-Routing in RR7
|
||||
- Separate Session-Cookies (Pfad/Domain-Lock)
|
||||
- Erst-Admin per Skript (37.2.8)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
# M035 — Plattform-Admin-Dashboard
|
||||
|
||||
**Block:** Block 1 · Modul 37
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 37.5
|
||||
|
||||
## Ziel
|
||||
Live-Dashboard mit Mandanten-Status-Verteilung, MRR-Trend, neue/verlorene Umsätze, System-Status (grün/gelb/rot), Aktivität, Lead-Pipeline-Volumen, Support-Status.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 37.5 — alle Dashboard-Kacheln + Zeitraum-Wechsler + Click-Through
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M034, M147 (Dashboard-Widget-Engine — Reuse)
|
||||
- **Wird benötigt von:** Plattform-Operations
|
||||
|
||||
## Out of Scope
|
||||
- Cohort-Analyse → Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
Dashboard lädt in <2 Sek; alle Kacheln zeigen Live-Daten; Zeitraum-Wechsler (24h/7d/30d/12mo) funktioniert.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Recharts (bereits in Boilerplate)
|
||||
- Caching pro Kachel mit TTL
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
# M036 — Mandanten-Verwaltung (Plattform-Admin)
|
||||
|
||||
**Block:** Block 1 · Modul 37
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 37.6, 37.14
|
||||
|
||||
## Ziel
|
||||
Liste + Detail aller Mandanten mit Status-Wechsel (mit Pflicht-Begründung), Notizen, Test-Phase-Verlängerung, Sonder-Konditionen, manuelle Mandanten-Anlage, Lösch-Anstoß im Auftrag.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 37.6 — Liste + Detail + Aktionen
|
||||
- 37.14 — Manuelle Mandanten-Anlage + Test-Phase-Verlängerung
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M034, M026, M153 (Stripe — für Sonder-Tarife)
|
||||
- **Wird benötigt von:** Plattform-Operations
|
||||
|
||||
## Out of Scope
|
||||
- Stellvertreter-Anmeldung → M037
|
||||
- Mandanten-Mitarbeiter-Verwaltung → M038
|
||||
|
||||
## Erfolgskriterium
|
||||
Plattform-Admin sperrt Mandant mit Begründung „Test-Account", Banner erscheint bei nächstem Login des Mandant-Admins; Manuelle Anlage funktioniert; Email-an-Admin verschickt.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Pflicht-Begründungs-Texte → Audit (37.18.1)
|
||||
- Lösch-Workflow im Auftrag (Mandanten-Admin bestätigt per Email-Link)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# M037 — Stellvertreter-Anmeldung („Login as")
|
||||
|
||||
**Block:** Block 1 · Modul 37
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 37.7
|
||||
|
||||
## Ziel
|
||||
Plattform-Admin mit spezieller Berechtigung kann sich kurzzeitig als Mandanten-Mitarbeiter einloggen (Begründungs-Pflicht, max 30 Min Session, sichtbares Banner für andere Mandanten-Mitarbeiter, voller Audit-Eintrag).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 37.7 — alle Punkte
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M034, M001 (Audit), M036
|
||||
- **Wird benötigt von:** Support-Workflow
|
||||
|
||||
## Out of Scope
|
||||
- Allgemeines Schreiben in Mandanten-Daten ohne Stellvertreter-Session bleibt verboten
|
||||
|
||||
## Erfolgskriterium
|
||||
Plattform-Admin loggt mit Begründung „Bug-Reproduktion Ticket 123" als Geerkens-Mitarbeiter ein; Banner sichtbar; nach 30 Min Auto-Logout; Audit-Eintrag dauerhaft mit Begründung.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Token-basierter Switch (kein Passwort-Sharing)
|
||||
- Banner in App-Shell mit Klartext (37.7.4)
|
||||
- Audit mit Pflicht-Begründungs-Feld (37.18.2)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M038 — Mandanten-Mitarbeiter-Verwaltung (Plattform-Admin)
|
||||
|
||||
**Block:** Block 1 · Modul 37
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 37.8
|
||||
|
||||
## Ziel
|
||||
Liste aller Mitarbeiter aller Mandanten. Aktionen: 2FA-Reset, Sessions beenden, Email ändern, Deaktivieren/Reaktivieren, Konto-Löschung im Auftrag, Wiederherstellung in 24h-Karenz.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 37.8 — alle Punkte
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M034, M022, M025
|
||||
- **Wird benötigt von:** Support-Workflow
|
||||
|
||||
## Erfolgskriterium
|
||||
Plattform-Admin findet User per Email-Suche, resettet 2FA mit Begründung; Audit-Eintrag korrekt; 24h-Wiederherstellung im Lösch-Workflow funktioniert.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Volltext-Suche über alle Mandanten
|
||||
- Aktionen mit Begründungs-Pflicht
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M039 — Plattform-Admin-Konten + Rollen
|
||||
|
||||
**Block:** Block 1 · Modul 37
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitte 37.3, 37.9
|
||||
|
||||
## Ziel
|
||||
Plattform-Admin-Konten verwalten (Standard-Rollen: Super-Admin, Support, Vertrieb, Engineering, Betrachter). Anlegen mit Pflicht-2FA-Setup-Link. 2FA-Reset durch anderen Super-Admin. Letzter Super-Admin nicht entfernbar.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 37.3 — Rollen-Modell intern
|
||||
- 37.9 — Konto-Verwaltung
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M034, M023 (Rollen-Engine wiederverwendet)
|
||||
- **Wird benötigt von:** Plattform-Operations
|
||||
|
||||
## Erfolgskriterium
|
||||
Super-Admin lädt neuen Plattform-Admin ein; Eingeladener muss bei Setup 2FA aktivieren; 2FA-Reset durch zweiten Super-Admin im Audit; letzter Super-Admin: Self-Demote blockiert (37.18.5).
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Eigene Rollen-Definition für Plattform-Admins (unabhängig von Mandanten-Rollen)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
# M040 — Interne Lead-Pipeline (HiveGrid-Verkäufe)
|
||||
|
||||
**Block:** Block 1 · Modul 37
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitt 37.13
|
||||
|
||||
## Ziel
|
||||
HiveGrid-eigene Lead-Liste (von Vertriebs-Pipeline der Mandanten strikt getrennt). Lead-Eingang über Webformular/Demo-Buchung/Email/Empfehlung/Manuell. Kanban mit Stufen Erstgespräch→Demo→Angebot→Verhandlung→Gewonnen→Verloren. „Promote-to-Tenant"-Funktion.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 37.13 — alle Punkte
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M034, M036, M147 (Dashboard-Reuse)
|
||||
- **Wird benötigt von:** Plattform-Vertrieb
|
||||
|
||||
## Out of Scope
|
||||
- Marketing-Automatisierung für Trial-Konversion → Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
Lead aus Marketing-Form landet in Liste; Kanban-Drag funktioniert; „Gewonnen → Promote-to-Tenant" führt zu manueller Mandanten-Anlage mit Verknüpfung.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Strikt getrennte DB-Tabellen (kein Cross-Reference zu Mandanten-Vertrieb)
|
||||
- Lead-Source-Adapter (Re-Use Apps-Engine?)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
+93
@@ -0,0 +1,93 @@
|
||||
# M041 — System-Health + Audit-Anzeige + Datenschutz + Support
|
||||
|
||||
**Block:** Block 1 · Modul 37
|
||||
**Pflichtenheft-Quelle:** block1.md Abschnitte 37.10, 37.11, 37.12, 37.15, 37.16
|
||||
|
||||
## Ziel
|
||||
- System-Health: Service-Status + Hintergrund-Aufgaben + KWP-Sync pro Mandant + Top-10-Fehler
|
||||
- Audit: plattformweite Sicht auf Plattform-Admin- + Mandanten-Audit-Logs
|
||||
- Datenschutz: Auftragsverarbeiter-Liste + AVV-Versionen mit Re-Akzeptanz-Aufforderung
|
||||
- Support: Ticket-Eingang + Antworten + interne Notizen
|
||||
- Abo-Verwaltung (37.10)
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 37.10 — Abo-Verwaltung mit Stripe-Sync-Vergleich
|
||||
- 37.11 — System-Health
|
||||
- 37.12 — Plattform-weites Audit
|
||||
- 37.15 — Support
|
||||
- 37.16 — Datenschutz-Verwaltung
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M034, M001, M151 (Audit-Anzeige Wiederverwendung), M153 (Stripe), M174 (Help-Desk)
|
||||
- **Wird benötigt von:** Plattform-Operations
|
||||
|
||||
## Out of Scope
|
||||
- Vollständiger Helpdesk-Workflow mit SLA → Phase 2
|
||||
- Cohorten-Analyse → Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
Health-Dashboard zeigt KWP-Heartbeat-Status pro Mandant; Audit-Volltext-Suche funktioniert; Support-Ticket per Email→automatisch zugeordnet; AVV-V2-Upload löst Re-Akzeptanz-Email an alle Mandanten-Admins aus.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Stripe-Diff-View (Klartext-Vergleich bei Abweichung — 37.18.8)
|
||||
- Aufbewahrungs-Frist 24 Monate (37.12.6)
|
||||
- Massen-Email an Mandanten-Admins mit Pre-Send-Pflicht (37.18.10)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,89 @@
|
||||
# M042 — Kontakt-Stammdaten
|
||||
|
||||
**Block:** Block 2 — Stammdaten · Modul 1 (CRM-Kern)
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/blocks/block2.md` Abschnitt 1.1, 1.5
|
||||
|
||||
## Ziel
|
||||
Personen-CRUD: Anrede, Titel, Name, Mehrfach-Email/Telefon mit Typ, Adresse, Geburtstag, Sprache, Verantwortlicher, Quelle, Privatkunde/Geschäft. Inline-Edit, Quick-Actions (Anruf, Mail, Termin, Aufgabe).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 1.1 — alle Stammdaten + Pflichtfelder + Mehrfach-Werte
|
||||
- 1.5 — Detail-Ansicht mit Inline-Edit und Quick-Actions
|
||||
- 1.10 — Permission-Stufen (Eigene/Alle, Bearbeiten, Admin)
|
||||
- 1.13 — Klartext-Fehlertexte
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001, M004 (Permissions), M013 (View-Models), M015 (UI-Layer)
|
||||
- **Wird benötigt von:** M043, M044, alle Module mit Kontakt-Verknüpfung
|
||||
|
||||
## Out of Scope
|
||||
- Firma → M043
|
||||
- Schlagwörter/Custom-Felder → M044
|
||||
- Listen-Ansicht → M046
|
||||
|
||||
## Erfolgskriterium
|
||||
Kontakt mit Pflichtfeldern angelegt, Inline-Edit funktioniert, 404 statt 403 bei fremdem Zugriff (1.10.1), Endgültig-Löschen mit Verknüpfungs-Auflistung.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Mehrfach-Email/Telefon-Schema mit Primär-Markierung
|
||||
- Multi-Firma-Verknüpfung mit Rolle (1.1.3)
|
||||
- Archivieren vs. Löschen Pattern (1.1.6)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M043 — Firma-Stammdaten + Hierarchie
|
||||
|
||||
**Block:** Block 2 · Modul 1
|
||||
**Pflichtenheft-Quelle:** block2.md Abschnitt 1.2, 1.6
|
||||
|
||||
## Ziel
|
||||
Firma-CRUD: Name, Rechtsform, USt-IdNr, Branche, Webseite, Standort. Verknüpfte Kontakte mit Rolle, primärer Ansprechpartner. Aktivitäts-Verlauf zeigt auch Aktivitäten der Kontakte.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 1.2 — Firma-Stammdaten
|
||||
- 1.6 — Detail-Ansicht (kontakte verwalten, Aktivitäts-Aggregation)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M042
|
||||
- **Wird benötigt von:** M044, M053 (Sales-Pipeline-Verknüpfung), M060 (Auftrag)
|
||||
|
||||
## Erfolgskriterium
|
||||
Firma anlegen, mehrere Kontakte verknüpfen, Rolle pro Kontakt; Aktivitäts-Verlauf zeigt Activity-Summe der verknüpften Kontakte.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Mutter-Tochter-Hierarchie als optionales Feld
|
||||
- Primär-Ansprechpartner-Logik
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,88 @@
|
||||
# M044 — Schlagwörter + Custom-Felder + Datenherkunft
|
||||
|
||||
**Block:** Block 2 · Modul 1
|
||||
**Pflichtenheft-Quelle:** block2.md Abschnitte 1.3, 1.9, 1.5.4 (Notizen)
|
||||
|
||||
## Ziel
|
||||
Tags mit 8 Standard-Farben, ad-hoc + verwaltet. Custom-Felder pro Workspace (Text, Zahl, Datum, Auswahl, Mehrfach, Bool, URL, Email) für Kontakte/Firmen/Leads getrennt konfigurierbar. SHK-Standard-Custom-Felder beim neuen Mandanten (1.1.5).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 1.3 — Custom-Felder pro Workspace
|
||||
- 1.9 — Tags
|
||||
- 1.5.4 — Notizen Markdown
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M042, M043
|
||||
- **Wird benötigt von:** alle Module mit Tag/Custom-Feld-Verknüpfung
|
||||
|
||||
## Out of Scope
|
||||
- Custom-Felder als Automation-Trigger → Phase 2 (1.12.3)
|
||||
- Erweiterte Validierung → Phase 2 (1.12.4)
|
||||
- Feld-spezifische Permissions → Phase 2 (1.12.5)
|
||||
|
||||
## Erfolgskriterium
|
||||
Tag „VIP" ad-hoc per Eingabe + Vorschlag-Knopf angelegt; Custom-Feld „Heizungsanlage Hersteller" als Pflicht setzbar; Tag-Merge-Funktion vereinigt Verwendungen.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Tag-Schema mit Color-Constraint (8 Farben)
|
||||
- Custom-Field-Definition als JSON-Schema
|
||||
- SHK-Standard-Felder als Konfigurations-Datei (Bauprinzip A.3)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M045 — Aktivitäts-Stream
|
||||
|
||||
**Block:** Block 2 · Modul 1
|
||||
**Pflichtenheft-Quelle:** block2.md Abschnitt 1.7
|
||||
|
||||
## Ziel
|
||||
Chronologischer Verlauf an Kontakten/Firmen/Leads/Verkaufsfällen/Projekten. Erfasst automatisch: Anrufe, Emails, Notizen, Tag-Wechsel, Verantwortlichen-Wechsel, Stage-Wechsel, Datei-Uploads, Forms, Aufgaben, Termine, Lead-Übernahmen, Won/Lost, Automationen, KI-Aktionen.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 1.7.1-1.7.7 — alle Punkte
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M042, M001 (Audit als Datenquelle), M004 (Permission-aware)
|
||||
- **Wird benötigt von:** M046, alle „Detail-Ansichten" anderer Entitäten
|
||||
|
||||
## Erfolgskriterium
|
||||
Aktivitäts-Eintrag pro System-Event automatisch erstellt; Filter nach Typ/Mitarbeiter/Zeitraum; Gruppierung „heute/gestern/diese Woche/älter"; Lese-Schutz bei verbotenem Cross-Tenant-Zugriff (1.7.7).
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Activity-Stream als unveränderlicher Append-only Log
|
||||
- Re-use Audit-Daten wo möglich (M001)
|
||||
- Volltext-Such-Index (re-use M056)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,87 @@
|
||||
# M046 — Listen + Segmente + DSGVO-Felder
|
||||
|
||||
**Block:** Block 2 · Modul 1
|
||||
**Pflichtenheft-Quelle:** block2.md Abschnitte 1.4, 1.5.8, 1.8
|
||||
|
||||
## Ziel
|
||||
Listen-Ansichten mit Filtern, Sortierung, Spalten-Konfiguration, Sammel-Aktionen, „Mehr laden" für 10K+. Duplikat-Erkennung mit Klartext-Hinweis + Merge-Tool. DSGVO-Export pro Kontakt als ZIP.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 1.4 — Listen-Ansichten + Filter + Sammel-Aktionen
|
||||
- 1.5.7-1.5.8 — Lösch-Bestätigung + DSGVO-Export
|
||||
- 1.8 — Suche + Duplikat-Erkennung mit Merge
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M042-M045, M056 (Suche)
|
||||
- **Wird benötigt von:** Lead-Liste, alle „Listen-Module"
|
||||
|
||||
## Out of Scope
|
||||
- KI-Smart-Match → Phase 2 (1.12.1)
|
||||
- Auto-Merge-Regeln → Phase 2 (1.12.2)
|
||||
|
||||
## Erfolgskriterium
|
||||
Liste mit 10K+ Einträgen läuft flüssig (Mehr-Laden); Sammel-Tag-Setzen für 200 Kontakte; Duplikat-Tool zeigt Treffer-Paar nebeneinander mit Aktivitäten-Anzahl.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Cursor-Pagination für große Listen
|
||||
- Filter-DSL kombinierbar (UND/ODER mit Klammer)
|
||||
- Merge-UI mit Field-by-Field-Wahl (1.8.5)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,86 @@
|
||||
# M047 — Lead-Inbox + Quellen-Adapter
|
||||
|
||||
**Block:** Block 2 · Modul 2
|
||||
**Pflichtenheft-Quelle:** block2.md Abschnitte 2.1, 2.2
|
||||
|
||||
## Ziel
|
||||
Lead-Schema mit Quellen-Adaptern (Form, Email, Telefon, Manuell, Apps-Engine). Pro Quelle Standard-Verantwortlicher + Standard-Tags. Live-Aktualisierung der Inbox.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 2.1 — Lead-Definition + Quellen
|
||||
- 2.2 — Auto-Anlage pro Quelle (Form, Email, Anruf, Manuell, Apps-Engine)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M008-M010 (Apps-Engine), M042 (Kontakt für Match)
|
||||
- **Wird benötigt von:** M048-M051
|
||||
|
||||
## Out of Scope
|
||||
- WhatsApp → Phase 2
|
||||
- CSV/JSON-Import → Phase 2 (2.12.1)
|
||||
|
||||
## Erfolgskriterium
|
||||
Form-Submit erzeugt Lead live in Inbox; Email an Mailbox von unbekanntem Absender wird Lead; Telefon-Anruf von unbekannter Nummer wird Lead mit Aufzeichnungs-Link.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Quellen-Adapter via Apps-Engine (M008)
|
||||
- Kontakt-Match-Probe beim Eingang
|
||||
- Real-Time-Updates (websocket via packages/realtime)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M048 — Lead-Routing pro Quelle [N4]
|
||||
|
||||
**Block:** Block 2 · Modul 2
|
||||
**Pflichtenheft-Quelle:** block2.md Abschnitt 2.11 [N4, 09.05.2026]
|
||||
|
||||
## Ziel
|
||||
Mandanten-konfigurierbares Routing pro Quelle: Status-Default, Verantwortlicher (Person/Round-Robin), Tags, Auto-Verkaufsfall mit Pipeline-Wahl + Bedingungen.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 2.11.1-2.11.6 — alles [N4]
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M047, M053 (Sales-Pipeline für Auto-Verkaufsfall)
|
||||
- **Wird benötigt von:** M049
|
||||
|
||||
## Erfolgskriterium
|
||||
Beispiel Geerkens (2.11.4): Form „Kontaktformular Webseite" → Status „Neu", Round-Robin Vertriebs-Team, Tag „Webseite", Auto-Verkaufsfall in „Anlagen-Verkauf" Pipeline; Routing-Aktionen im Lead-Activity-Log mit Klartext.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Routing-Regel-DSL mit Bedingungs-Kombinatoren
|
||||
- Reihenfolge-Auswertung (erste Treffer-Regel)
|
||||
- Round-Robin-State pro Gruppe
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,82 @@
|
||||
# M049 — Auto-Verkaufsfall-Anlage
|
||||
|
||||
**Block:** Block 2 · Modul 2 + Modul 3
|
||||
**Pflichtenheft-Quelle:** block2.md 2.11.2 + block3.md Modul 3.7
|
||||
|
||||
## Ziel
|
||||
Aus qualifiziertem Lead automatisch Verkaufsfall in Ziel-Pipeline anlegen mit vorausgefüllten Daten. Routing-Regeln (M048) entscheiden Pipeline + Stufe.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 2.5 — Übernahme-Modal (manuell)
|
||||
- 2.11.2 — Auto-Anlage durch Routing
|
||||
- 3.7 — Quellen-Liste für Verkaufsfall (inkl. Lead, Form, Email, Anruf, Automation)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M047, M048, M060 (Verkaufsfall-CRUD)
|
||||
- **Wird benötigt von:** Geerkens-Workflow
|
||||
|
||||
## Erfolgskriterium
|
||||
Form-Submit „PV-Konfigurator" mit Volumen-Feld → Auto-Verkaufsfall in Premium-Pipeline mit Volumen vorausgefüllt + Activity-Log-Eintrag.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Auto-Anlage als Routing-Action in M048
|
||||
- Daten-Mapping pro Form-Feld konfigurierbar
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
# M050 — Spam/Duplikat-Erkennung
|
||||
|
||||
**Block:** Block 2 · Modul 2
|
||||
**Pflichtenheft-Quelle:** block2.md Abschnitte 2.7, 2.8
|
||||
|
||||
## Ziel
|
||||
Spam-Schutz pro Quelle (Stundenlimit, IP-Limit, Anomalie 10x). Optionale Heuristiken (IP-Blocklist, Wegwerf-Mail, Honeypot, zu schnelle Submission). Auto-Lösch-Job nach 30 Tagen für Spam, 90 Tage für Verloren.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 2.7 — DSGVO-Auto-Löschung
|
||||
- 2.8 — Spam-Schutz mit konfigurierbaren Heuristiken
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M047, M010 (Apps-Engine Webhook-Schutz analog)
|
||||
- **Wird benötigt von:** stabile Lead-Inbox
|
||||
|
||||
## Out of Scope
|
||||
- KI-Smart-Match → Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
Form-Flut mit 247 Submissions/5 Min → Quelle pausiert + Klartext-Notification (2.8.3); Spam-Lead nach 30 Tagen Auto-gelöscht mit anonymisiertem Activity-Eintrag.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Per-Source Rate-Limit + IP-Limit
|
||||
- Anomalie-Detector wiederverwendbar (re-use M010)
|
||||
- BullMQ-cron für Auto-Lösch-Job
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,86 @@
|
||||
# M051 — Lead-Status-Pipeline + Verlust-Gründe + Notifications
|
||||
|
||||
**Block:** Block 2 · Modul 2
|
||||
**Pflichtenheft-Quelle:** block2.md Abschnitte 2.3-2.6, 2.9, 2.10
|
||||
|
||||
## Ziel
|
||||
Status-Verlauf (Neu→Qualifiziert→Übernommen / Verloren / Spam). Listen-Detail-UI mit Quick-Actions, Sammel-Aktionen mit gemischten-Rechte-Hinweis. Statistik-Seite + CSV-Export.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 2.3 — Listen-Ansicht
|
||||
- 2.4 — Detail mit Quick-Actions
|
||||
- 2.5 — Übernahme zu Kontakt
|
||||
- 2.6 — Status-Übergänge mit Begründungs-Pflicht
|
||||
- 2.9 — Lead-Statistiken
|
||||
- 2.10 — Permissions
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M047-M050, M042 (Kontakt für Übernahme)
|
||||
- **Wird benötigt von:** Geerkens-Lead-Workflow
|
||||
|
||||
## Erfolgskriterium
|
||||
Lead durchläuft alle Status-Übergänge; Übernahme-Modal legt Kontakt + ggf. Firma + ggf. Verkaufsfall in einem Schritt an; Statistiken mit Aufschlüsselungen pro Quelle/Vertriebler.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Status-State-Machine mit Begründungs-Pflichten
|
||||
- Übernahme-Modal mit Sub-Forms (Kontakt, Firma, Verkaufsfall)
|
||||
- Sammel-Aktionen mit Pre-Check (2.10.1)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M052 — Datei-Upload (Anti-Virus + Format-Whitelist)
|
||||
|
||||
**Block:** Block 2 · Modul 23
|
||||
**Pflichtenheft-Quelle:** block2.md Modul 23 (Block 2 zweite Hälfte — wird beim TC-Plan vor Ort gelesen)
|
||||
|
||||
## Ziel
|
||||
Datei-Upload mit Anti-Virus-Scan (ClamAV-EU oder vergleichbar), Format-Whitelist, Max-Size-Limit, Foto-Auto-Compression.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- Modul 23 Sektionen 23.1-23.4 (Upload-Pfad, Validierung)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001, M004
|
||||
- **Wird benötigt von:** M053-M055, M095 (KWP-Archiv-Sync), M137 (Customer-Portal-Upload), M092 (Email-Anhänge)
|
||||
|
||||
## Erfolgskriterium
|
||||
Upload mit Standard-Format funktioniert; .exe abgelehnt mit Klartext; Foto >10MB auto-compressed.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Browser-Image-Compression (`browser-image-compression` ist in Boilerplate-Deps)
|
||||
- Anti-Virus über externes EU-Service oder ClamAV-Self-Hosted
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,82 @@
|
||||
# M053 — Speicher-Backend (S3 auf Scaleway)
|
||||
|
||||
**Block:** Block 2 · Modul 23
|
||||
**Pflichtenheft-Quelle:** block2.md Modul 23 + Bauprinzip A.12
|
||||
|
||||
## Ziel
|
||||
S3-kompatibler Storage auf Scaleway (EU). Pro-Tenant-Bucket-Pfad. Signed-URLs für temporären Read-Zugriff.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.12.1 — Hosting Scaleway
|
||||
- 27.2.2 — Mandanten-Trennung gilt für Dateien
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M052
|
||||
- **Wird benötigt von:** M054, M055
|
||||
|
||||
## Erfolgskriterium
|
||||
Datei landet in `s3://bucket/tenant_<id>/<file-id>`; Signed-URL läuft nach Konfiguration ab; Cross-Tenant-Read-Versuch blockiert.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- `packages/storage` (bereits in Boilerplate)
|
||||
- Scaleway Object-Storage (S3-kompatibel)
|
||||
- Pre-signed-URL TTL konfigurierbar
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M054 — Datei: Permissions + Sharing + Versionierung
|
||||
|
||||
**Block:** Block 2 · Modul 23
|
||||
**Pflichtenheft-Quelle:** block2.md Modul 23
|
||||
|
||||
## Ziel
|
||||
Pro-Datei-Permissions (sichtbar für Rollen/Personen). Sharing-Link mit Ablaufdatum. Versionierung (frühere Versionen aufbewahren).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- Modul 23 Sektionen Permissions + Versionierung
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M052, M053, M004 (Permission-Wrapper)
|
||||
- **Wird benötigt von:** M055, alle Module mit Datei-Verknüpfung
|
||||
|
||||
## Erfolgskriterium
|
||||
Datei mit Permission „nur Projekt-Mitglieder" sichtbar nur für diese; Share-Link läuft am gewählten Datum ab; vorherige Version restorebar.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Permission-Layer auf Datei-Ebene
|
||||
- Version-Snapshots mit Diff-Anzeige
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M055 — Datei: Suche + Tagging + Archivierung
|
||||
|
||||
**Block:** Block 2 · Modul 23
|
||||
**Pflichtenheft-Quelle:** block2.md Modul 23
|
||||
|
||||
## Ziel
|
||||
Volltext-Suche in Dateien (PDF/Office), Tagging, Archivierungs-Workflow.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- Modul 23 Sektionen Suche + Archiv
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M052-M054, M056 (Suche)
|
||||
- **Wird benötigt von:** M058 (Such-UI), Geerkens-Datei-Workflow
|
||||
|
||||
## Erfolgskriterium
|
||||
PDF mit OCR-Text findbar in Such-Dialog; Archivierung blendet aus aktiver Sicht aus.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- OCR-Pipeline (Phase 1 evtl. Tesseract; Phase 2 EU-OCR-API)
|
||||
- Tag-Re-use (M044)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M056 — Globale Suche: Such-Index
|
||||
|
||||
**Block:** Block 2 · Modul 24
|
||||
**Pflichtenheft-Quelle:** block2.md Modul 24
|
||||
|
||||
## Ziel
|
||||
Such-Index über Kontakte, Firmen, Leads, Verkaufsfälle, Aufträge, Aufgaben, Dateien, Notizen. Postgres FTS oder Meilisearch.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- Modul 24 Sektionen Index + Volltext
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M042-M046
|
||||
- **Wird benötigt von:** M057, M058
|
||||
|
||||
## Erfolgskriterium
|
||||
Index-Refresh bei Datensatz-Änderung; <500ms für 100K+ Datensätze.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Postgres FTS bevorzugen (kein Extra-Service)
|
||||
- Update-Trigger via Prisma-Middleware (re-use M001)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M057 — Globale Suche: Permission-aware
|
||||
|
||||
**Block:** Block 2 · Modul 24
|
||||
**Pflichtenheft-Quelle:** block2.md Modul 24 + A.5
|
||||
|
||||
## Ziel
|
||||
Suche zeigt nur Treffer, die der User sehen darf — kein Leak via Snippet/Highlight.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.5.1 — auch in Suche darf nur sichtbar werden, was Recht hat
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M056, M004
|
||||
- **Wird benötigt von:** M058
|
||||
|
||||
## Erfolgskriterium
|
||||
Vertriebler ohne CRM-Recht: Such-Treffer für Kontakt erscheint nicht; Volume-Feld in Verkaufsfall: Snippet ohne Volume-Wert für unberechtigten User (3.11.4).
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Filter im SQL-Query, nicht erst im Result
|
||||
- Field-Level-Redact für Snippets
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M058 — Globale Suche: UI + Saved-Searches
|
||||
|
||||
**Block:** Block 2 · Modul 24
|
||||
**Pflichtenheft-Quelle:** block2.md Modul 24
|
||||
|
||||
## Ziel
|
||||
Cmd-K-Suche-Overlay (kbar). Filter pro Entität. Bis 5 Saved-Searches pro User. Such-Verlauf.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- Modul 24 Such-UI
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M056, M057, M015 (UI-Layer)
|
||||
- **Wird benötigt von:** Geerkens-Daily-Workflow
|
||||
|
||||
## Erfolgskriterium
|
||||
Cmd-K öffnet Suche; Treffer kategorisiert (Kontakte, Verkaufsfälle, Aufträge); Saved-Search „Meine offenen Leads" persistiert.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- `kbar` ist in Boilerplate-Deps
|
||||
- Saved-Search-Schema pro User
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M059 — Sales-Pipeline: Konfiguration + SHK-Standard-Pipeline
|
||||
|
||||
**Block:** Block 3 · Modul 3
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitt 3.2
|
||||
|
||||
## Ziel
|
||||
Pipeline-CRUD mit Stufen, Stufen-Typen (offen/gewonnen/verloren), Wahrscheinlichkeit, Stuck-Schwelle, Farbe. Drag-&-Drop für Reihenfolge. SHK-Standard-Pipelines beim neuen Mandanten.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 3.2.1-3.2.9 — alle Punkte
|
||||
- 3.13.1-3.13.3 — Klartext-Fehlertexte (keine Gewonnen-Stufe etc.)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001, M004, M158 (SHK-Provisionierung)
|
||||
- **Wird benötigt von:** M060-M064
|
||||
|
||||
## Erfolgskriterium
|
||||
Mandant kann „Anlagen-Verkauf" + „Wartungsverträge" Pipelines parallel führen; Stufe ohne Gewonnen-Typ → Klartext-Block; Drag-&-Drop sortiert Stufen.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Pipeline-Schema in Prisma
|
||||
- Standard-Pipeline-Definition als Konfigurations-Datei (Bauprinzip A.3)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
# M060 — Verkaufsfall-CRUD + Pflichtfeld Vertriebler [N6]
|
||||
|
||||
**Block:** Block 3 · Modul 3
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitte 3.1, 3.5, 3.7, 3.9
|
||||
|
||||
## Ziel
|
||||
Verkaufsfall mit eindeutiger Nummer (D-2026-0042), Titel, Pipeline/Stufe, Volumen, Termin, Pflichtfeld-Vertriebler [N6], verknüpfter Kontakt + optional Firma. Anlage manuell + aus Lead/Form/Email/Anruf/Automation. Stufen-Übergänge mit Begründungs-Pflicht (Verloren) + 24h-Undo (Gewonnen/Verloren).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 3.1 — Stammdaten + Vertriebler-Pflicht [N6]
|
||||
- 3.5 — Stufen-Übergänge + 24h-Undo
|
||||
- 3.7 — Quellen
|
||||
- 3.9.4 — Klartext-Banner pro Zustand
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M042, M043, M059
|
||||
- **Wird benötigt von:** M061-M064
|
||||
|
||||
## Erfolgskriterium
|
||||
Verkaufsfall mit Pflichtfeldern angelegt, Vertriebler-Default aus Routing (M048); Stufen-Wechsel mit Begründungs-Pflicht + 24h-Undo funktioniert.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Sequenz-Generator für Verkaufsfall-Nummer
|
||||
- Quick-Action „Termin anlegen mit Daten-Übergabe" (3.9.5 [N17])
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,82 @@
|
||||
# M061 — Sales-Pipeline: Kanban-UI + Drag&Drop
|
||||
|
||||
**Block:** Block 3 · Modul 3
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitt 3.4, 3.11
|
||||
|
||||
## Ziel
|
||||
Kanban-Spalten pro Stufe mit Live-Aktualisierung, Drag-&-Drop, Karten-Inhalt (Titel, Volumen falls Recht, Verantwortlicher, Tags, Stuck-Indikator). Tabellen-Ansicht alternativ. Cross-Pipeline-Sicht. Suche + Filter + Sammel-Aktionen + CSV-Export.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 3.4.1-3.4.11 — alle Punkte
|
||||
- 3.11.1-3.11.6 — Permission-Stufen mit Volumen-Sonderregel
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M060, M015 (UI), M057 (Permission-aware Search)
|
||||
- **Wird benötigt von:** Geerkens-Daily-Workflow
|
||||
|
||||
## Erfolgskriterium
|
||||
Kanban zeigt 200 Verkaufsfälle flüssig; Drag-&-Drop zwischen Stufen; Bauleiter sieht Karten OHNE Volumen (3.11.4); Live-Updates wenn anderer User Karte verschiebt.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- `react-beautiful-dnd` oder `react-dnd` (in Boilerplate-Deps)
|
||||
- Field-Level-Redact für Volumen
|
||||
- WebSocket via packages/realtime
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M062 — Sales-Pipeline: Verlust/Gewinn-Gründe [N8]
|
||||
|
||||
**Block:** Block 3 · Modul 3
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitt 3.3 [N8, 09.05.2026]
|
||||
|
||||
## Ziel
|
||||
Mandanten-pflegbare Verlust- und Gewinn-Gründe (Pflicht/Optional pro Mandant einstellbar). 5 SHK-Standard-Gründe je Liste beim neuen Mandanten. Auswertungs-Aggregation pro Grund.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 3.3.1-3.3.5 — alle Punkte [N8]
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M060, M158 (SHK-Provisionierung)
|
||||
- **Wird benötigt von:** M064 (Reporting)
|
||||
|
||||
## Erfolgskriterium
|
||||
Mandanten-Admin pflegt Gründe; Verloren-Markierung verlangt Grund (oder optional je Mandanten-Setting); Auswertung „Top-3-Verlust-Gründe pro Vertriebler" zeigt Häufigkeiten.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Archivierbar, nicht hart löschbar (sonst Auswertungen brechen)
|
||||
- Konfigurations-Toggle „Pflicht/Optional" pro Liste
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# M063 — Auto-Auftragsprojekt [N7] + Setter-Closer [N17]
|
||||
|
||||
**Block:** Block 3 · Modul 3
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitte 3.6, 3.9.5 [N7, N17, N9]
|
||||
|
||||
## Ziel
|
||||
Won-Handoff zur Auftragspipeline mit Pipeline/Stufen-Wahl. Mandanten-Konfiguration: Projekt-Anlage bei Gewonnen ODER bei Verkaufsfall-Anlage [N7]. Setter-Closer-Termin direkt aus Verkaufsfall mit Auto-Daten-Übernahme [N17]. Wartung/Service explizit kein Projekt [N9].
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 3.6.1-3.6.7 — Won-Handoff + Mandanten-Konfiguration [N7] + Wartung/Service-Hinweis [N9]
|
||||
- 3.9.5 — Setter-Closer-Workflow [N17]
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M060, M065 (Auftragspipeline-Konfig), M119 (Calendar-Sync)
|
||||
- **Wird benötigt von:** M064
|
||||
|
||||
## Out of Scope
|
||||
- Service-Modul → Phase 2 [N9]
|
||||
|
||||
## Erfolgskriterium
|
||||
Won-Verkaufsfall → Modal mit „Projekt anlegen?" → Auftragspipeline-Wahl + Anlage in einem Schritt; Setter klickt im Verkaufsfall „Termin für Closer" → Termin mit Adresse/Volumen/Fotos vorausgefüllt im Closer-Kalender.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Mandant-Konfig „Option A vs. B" (3.6.7)
|
||||
- Field-Mapping pro Sales-Pipeline → Termin-Layout (3.9.5)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M064 — Sales-Pipeline: Reporting + KWP-Sync
|
||||
|
||||
**Block:** Block 3 · Modul 3
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitte 3.8, 3.10
|
||||
|
||||
## Ziel
|
||||
Forecast (gewichtetes Volumen pro Stufe), realisierter Umsatz, Vertriebler-Kennzahlen, Stufen-Übergangs-Quoten, Verlust-Gründe-Verteilung. Stuck-Erkennung + Auto-Archivierung. Optional KWP-Sync für gewonnene Verkaufsfälle (Wartungs-Verträge ausgenommen [N9]).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 3.8 — Stuck + Auto-Archivierung
|
||||
- 3.10 — Forecast + KPIs
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M060, M062, M063, M147 (Dashboard für Widgets)
|
||||
- **Wird benötigt von:** GF-Dashboard, KWP-Anbindung
|
||||
|
||||
## Erfolgskriterium
|
||||
Forecast-Berechnung über alle Pipelines stimmt; Stuck-Verkaufsfälle als Liste; Verloren-Verkaufsfälle nach 90d auto-archiviert.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Tägliche Stuck-/Archiv-Jobs (BullMQ-cron)
|
||||
- Forecast-Aggregation als View oder berechnete Spalte
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M065 — Auftragspipeline: Konfiguration
|
||||
|
||||
**Block:** Block 3 · Modul 4
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitt 4.2, 4.3
|
||||
|
||||
## Ziel
|
||||
Auftrags-Pipelines mit Stufen + Abnahme-Pflicht-Stufe (4.2.3-4.2.4). SHK-Standard: Anlagen-Installation, Wartungseinsatz, Notfall-Reparatur. Projekt-Vorlagen (Default-Pipeline, Mitarbeiter-Rollen, Aufgaben, Plantafel-Einträge, Custom-Felder).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 4.2 — Pipeline-Konfig + Abnahme-Pflicht
|
||||
- 4.3 — Projekt-Vorlagen
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001, M004, M059 (Pipeline-Engine reuse)
|
||||
- **Wird benötigt von:** M066-M070
|
||||
|
||||
## Erfolgskriterium
|
||||
Mandant kann 3 SHK-Standard-Pipelines mit korrekten Stufen + Abnahme-Pflicht setzen; Vorlage „Standard-Anlagen-Installation" füllt neue Projekte mit 3 Mitarbeiter-Rollen + 6 Default-Tasks.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Stufen-Typ „erfordert Abnahme" als Flag
|
||||
- Vorlagen als Konfigurations-Daten (A.3)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,86 @@
|
||||
# M066 — Auftrag-CRUD + KWP-Dokumenten-Archiv [N5]
|
||||
|
||||
**Block:** Block 3 · Modul 4
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitte 4.1, 4.4, 4.5, 4.8, 4.9, 4.12
|
||||
|
||||
## Ziel
|
||||
Auftragsprojekt mit eindeutiger Nummer (P-2026-0042), Pipeline/Stufe, Volumen, Geplanter/Tatsächlicher End-Termin, Baustellen-Adresse, Projektleiter, Mitarbeiter-Liste, Ursprung-Verkaufsfall (optional), Stornierungs-Grund. Anlage manuell + aus Won-Handoff + Form + Booking + Notfall-Anruf + Automation. Detail-Ansicht mit Sales-Verlauf-Sektion read-only. Hard-Delete-Block bei Abnahme-Protokollen.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 4.1 — Stammdaten
|
||||
- 4.4 — Quellen
|
||||
- 4.5 — Spalten/Tabellen-Ansicht mit Drag-&-Drop
|
||||
- 4.8 — Detail-Ansicht inkl. Sales-Verlauf-Sektion read-only mit Volumen-Permission-Schutz
|
||||
- 4.9 — Lifecycle (Vor/Rück-Wechsel, Storno-Grund-Pflicht, Hard-Delete-Block bei Aufbewahrung)
|
||||
- 4.12 — Modul-Integration (CRM, Sales, Forms, Booking, Email, Telefonie, Chat, HR, Customer-Portal, Automation, KWP, Notifications, Dateien, Calendar, Aufgaben)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M042, M043, M060 (Verkaufsfall), M065, M095 (KWP-Archiv-Sync), M052-M055 (Dateien)
|
||||
- **Wird benötigt von:** M067-M070
|
||||
|
||||
## Erfolgskriterium
|
||||
Won-Handoff legt Projekt + automatischen Chat-Channel an (4.12.7); Sales-Verlauf-Sektion read-only mit Volumen-Schutz für Bauleiter (4.8.4.4); Hard-Delete bei aufbewahrungspflichtigen Daten Klartext-blockiert.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Sequenz-Generator P-YYYY-NNNN
|
||||
- Sales-Verlauf-Sektion via View-Model-Composition
|
||||
- Mängel→Aufgaben-Auto-Erzeugung (4.12.15)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,82 @@
|
||||
# M067 — Plantafel mit Tagen-Granularität [N10]
|
||||
|
||||
**Block:** Block 3 · Modul 4
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitt 4.6 [N10, 09.05.2026]
|
||||
|
||||
## Ziel
|
||||
Wochenkalender-Plantafel (Tag/Woche/Monat) mit Mitarbeiter-Achse und Drag-&-Drop. Konflikt-Erkennung (Doppel-Belegung, Urlaub, Krankheit, außerhalb Verfügbarkeit). Verfügbarkeits-Regeln pro Mitarbeiter. Status-Verlauf pro Eintrag. Kalender-Sync, Mobile-Sicht „Meine Termine heute".
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 4.6.1-4.6.13 — Desktop-Plantafel + Konflikt-Erkennung + Verfügbarkeit + Mobile-Sicht
|
||||
- KWP-Sync (4.6.14) → M094
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M066, M129 (Krankmeldung), M135 (Urlaub), M119 (Calendar-Sync)
|
||||
- **Wird benötigt von:** M068, M094 (KWP-Plantafel-Sync)
|
||||
|
||||
## Erfolgskriterium
|
||||
Drag-Move erkennt Doppel-Belegung mit Klartext-Confirm; Krankmeldungs-Konflikt blockiert; Mobile-Sicht zeigt heutige Einsätze mit Karten-Link + Status-Wechsel-Knopf.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- xyflow oder eigene Calendar-Grid-Component
|
||||
- Konflikt-Detector mit allen Regeln aus 4.6.9
|
||||
- Push bei neuer Zuweisung (4.6.13.5)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M068 — Auftrag: Mitglieder-Mgmt + Rollen pro Auftrag
|
||||
|
||||
**Block:** Block 3 · Modul 4
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitt 4.10
|
||||
|
||||
## Ziel
|
||||
Mitarbeiter pro Projekt zuweisen mit Rolle (Projektleiter, Bauleiter, Monteur, Lehrling, frei beschriftbar). Gruppen-Add-Funktion. Auto-Add zum Projekt-Team-Chat (M104). Klartext-Hinweis bei leerem Team.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 4.10.1-4.10.4
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M066, M104 (Channel-Modell)
|
||||
- **Wird benötigt von:** M067 (Plantafel braucht Mitglieder), M069
|
||||
|
||||
## Erfolgskriterium
|
||||
Gruppen-Add „Team Süd" fügt 5 Monteure hinzu + erstellt Projekt-Channel mit allen; leeres Team zeigt Klartext + Add-Knopf.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Rollen pro Projekt sind frei textuell (nicht globale Rolle)
|
||||
- Chat-Channel-Lifecycle bei Projekt-Abschluss → archivieren
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,82 @@
|
||||
# M069 — Auftrag: Abnahme-Workflow + Mängel-Liste
|
||||
|
||||
**Block:** Block 3 · Modul 4
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitt 4.7
|
||||
|
||||
## Ziel
|
||||
Mobile-first Abnahme-Protokoll mit Datum/Anwesende, technischen Werten, übergebenen Dokumenten, Mängel-Liste mit Foto, Touch-Unterschriften (Kunde + Monteur), Auto-PDF-Generierung, Auto-Email an Kunde. Mängel-Klassifizierung (kritisch/klein/kosmetisch) bestimmt Folge-Aktionen. Mehrere Abnahmen pro Projekt möglich (Teilabnahmen). Rechtliche Aufbewahrung 6 Jahre (kein Löschen).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 4.7.1-4.7.7 — alle Punkte
|
||||
- 4.14.1, 4.14.3, 4.14.5 — Klartext-Texte
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M066, M052-M055 (Dateien für Fotos), M121 (Form-Builder für Vorlage), M092 (Email-Versand), M158 (SHK-Standard-Formular), M073 (Aufgaben für Mängel-Auto-Erzeugung)
|
||||
- **Wird benötigt von:** Geerkens-Auftrags-Abschluss
|
||||
|
||||
## Erfolgskriterium
|
||||
Monteur füllt mobile Abnahme aus, Kunde unterschreibt per Touch, PDF generiert + per Email gesendet; Mit-Vorbehalt-Mängel werden auto-Aufgaben mit Frist; Hard-Delete blockiert (rechtliche Aufbewahrung).
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- `signature_pad` ist in Boilerplate-Deps
|
||||
- @react-pdf/renderer für PDF (in Boilerplate-Deps)
|
||||
- IP+Zeitstempel als Beweissicherung (4.7.3.3, 4.7.7.4)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# M070 — Auftrag: Material-Listen + Lager-Anbindung
|
||||
|
||||
**Block:** Block 3 · Modul 4
|
||||
**Pflichtenheft-Quelle:** block3.md (Material/Lager via 4.13.3 + Modul-Integrationen)
|
||||
|
||||
## Ziel
|
||||
Material-Listen pro Auftrag (Position, Menge, Status). Lager-Anbindung über Apps-Engine (Phase 1: KWP). Lagerist-Rolle (M023.1) sieht Material-Ausgang.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 4.13.3 — Detaillierte Material-Bestell-Verwaltung Phase 2 falls KWP nicht reicht — Phase 1 via KWP-Sync (M095)
|
||||
- M27.7 — Lagerist-Rolle [N1]
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M066, M095 (KWP-Material-Daten)
|
||||
- **Wird benötigt von:** Geerkens-Material-Workflow
|
||||
|
||||
## Out of Scope
|
||||
- Eigenes Material-Bestell-Modul → Phase 2 (4.13.3)
|
||||
|
||||
## Erfolgskriterium
|
||||
Lagerist sieht zugeordnete Material-Lieferungen pro Auftrag; Material-Ausgang dokumentierbar.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Lagerist-Permission-Cluster (M023.1)
|
||||
- KWP-Daten via M095 read-only
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
# M071 — Aufgaben-CRUD + Zuweisung
|
||||
|
||||
**Block:** Block 3 · Modul 26
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitte 26.1, 26.2, 26.4, 26.8
|
||||
|
||||
## Ziel
|
||||
Aufgabe mit Titel/Beschreibung/Verantwortlicher (Person ODER Gruppe — eines Pflicht), Frist, Priorität (niedrig/normal/hoch/dringend), Status (offen/in Arbeit/erledigt), Verknüpfung zur Haupt-Entität, Quelle, Beobachter-Liste. Listen-Ansichten (Meine/Von mir erstellt/Alle) mit Filter, Schnell-Aktionen, Sammel-Aktionen.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 26.1 — Stammdaten + Verantwortlicher-Pflicht
|
||||
- 26.2 — Listen-Ansichten + Filter
|
||||
- 26.4 — Detail-Ansicht
|
||||
- 26.8 — Permissions
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001, M004, M013-M015 (UI), M042 (Kontakt für Verknüpfung)
|
||||
- **Wird benötigt von:** M072-M074
|
||||
|
||||
## Erfolgskriterium
|
||||
Aufgabe ohne Verantwortlichen blockiert (oder Default = Ersteller laut 26.11.3); Sammel-Aktion „Status erledigt" für 50 Aufgaben; 404 statt 403 bei fremder Aufgabe.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Verantwortlicher kann Person ODER Gruppe (oneOf)
|
||||
- Standard-Sortierung: Frist asc + Priorität (26.2.9)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M072 — Aufgaben-Listen pro Modul (Inline)
|
||||
|
||||
**Block:** Block 3 · Modul 26
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitt 26.3, 26.5
|
||||
|
||||
## Ziel
|
||||
Aufgaben-Bereich an Kontakten/Firmen/Leads/Verkaufsfällen/Projekten. Direktes Anlegen aus Detail-Ansicht mit Auto-Verknüpfung. Quellen: Manuell, Chat-Nachricht „Als Aufgabe markieren", Form-Aktion mit Vorlage, Automation-Aktion.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 26.3 — Verknüpfungs-Bereiche
|
||||
- 26.5 — Quellen
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M071, M104 (Chat), M121 (Form-Builder), M075 (Automation für „Aufgabe erstellen"-Aktion)
|
||||
- **Wird benötigt von:** M073, alle Module mit Aufgaben-Anzeige
|
||||
|
||||
## Erfolgskriterium
|
||||
Aus Verkaufsfall „Aufgabe anlegen" → vorausgefüllt mit Verkaufsfall-Verknüpfung; Chat-Nachricht „Als Aufgabe markieren" erzeugt Aufgabe mit Beschreibung = Nachrichten-Inhalt + Chat-Eintrag „Aufgabe erstellt aus dieser Nachricht".
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Form-Aktion-Konfig mit Frist-Berechnung (26.5.3)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M073 — Aufgaben: Erinnerungen + Push + Email
|
||||
|
||||
**Block:** Block 3 · Modul 26
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitt 26.6, 26.7
|
||||
|
||||
## Ziel
|
||||
Auto-Erinnerungen 24h vor / bei / 24h nach Frist. Empfänger: Verantwortlicher + Beobachter. Bündelung max 1/4h pro User. Auto-Archivierung erledigt nach 30 Tagen.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 26.6 — Erinnerungen + Auto-Archivierung
|
||||
- 26.7 — Verlaufs-Strom-Integration
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M071, M072, M011 (Notifications)
|
||||
- **Wird benötigt von:** M074, Aufgaben-Workflow
|
||||
|
||||
## Erfolgskriterium
|
||||
Aufgabe mit Frist morgen → 1× Push heute; Bündelung verhindert >1 Notification pro 4h; erledigte Aufgabe nach 30d auto-archiviert.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- BullMQ-cron für Erinnerungen
|
||||
- Bündelungs-Window pro User
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M074 — Aufgaben-Sync mit ERP-Aufgaben-Welt [N11]
|
||||
|
||||
**Block:** Block 3 · Modul 26
|
||||
**Pflichtenheft-Quelle:** block3.md Abschnitt 26.10 [N11, 09.05.2026]
|
||||
|
||||
## Ziel
|
||||
Pro Mandant aktivierbar pro angebundenem ERP-Adapter. KWP-Box als Phase 1. Sync-Modi: A (Spiegel ERP→HiveGrid), B (Spiegel HiveGrid→ERP), C (bidirektional mit „KWP gewinnt"). Identifikations-Brücke pro Adapter konfigurierbar (KWP-Box: Email-Adresse). Visueller Marker („KWP" Badge). Klartext-Hinweis bei Sync-Aussetzern. Aushebel-Schutz.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 26.10.1-26.10.7 — alle Punkte
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M071-M073, M089-M093 (KWP-Sync-Foundation), M008-M010 (Apps-Engine)
|
||||
- **Wird benötigt von:** Geerkens-KWP-Aufgaben-Workflow
|
||||
|
||||
## Erfolgskriterium
|
||||
Mandanten-Admin aktiviert KWP-Sync Modus C; Aufgabe in HiveGrid → erscheint in KWP-Box; KWP-Box-erledigt → spiegelt zu HiveGrid mit Klartext „erledigt in KWP um [Zeit]".
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Per-Adapter-Sync-Konfiguration
|
||||
- Konflikt-Auflösung Re-use M093
|
||||
- Sync-Status-Marker im Aufgaben-Detail
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,87 @@
|
||||
# M075 — Automation: Schema + Auslöser-Registry
|
||||
|
||||
**Block:** Block 4 — USP-Säulen · Modul 17
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/blocks/block4.md` Abschnitte 17.1, 17.2
|
||||
|
||||
## Ziel
|
||||
Datenmodell für Automatisierungen + Registry aller Phase-1-Auslöser (CRM, Leads, Sales, Auftrag, Forms, Booking, Email, Telefonie, Aufgaben, Zeit, KWP, Apps-Engine, HR, Customer-Portal).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 17.1 — Aufbau (Auslöser, Bedingungen, Aktionen, Steuerung; aktiv/inaktiv; Erstellungs-Quelle)
|
||||
- 17.2 — Vollständige Auslöser-Liste (17.2.1-17.2.14)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M001 (Audit), M007 (Idempotenz), Module der Auslöser-Quellen müssen Events emittieren
|
||||
- **Wird benötigt von:** M076-M082, alle Module mit Trigger-Bedarf
|
||||
|
||||
## Out of Scope
|
||||
- Editor → M078
|
||||
- Schutz-Mechanismen → M081
|
||||
- Logs → M082
|
||||
|
||||
## Erfolgskriterium
|
||||
Test-Automation mit Auslöser „Lead empfangen" feuert bei Lead-Submit; Trigger-Eintrag im Audit-Log.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Auslöser-Registry als Plug-Architektur (Module registrieren sich)
|
||||
- Filter pro Auslöser (Pipeline, Stufe, Quelle, Schwellenwert)
|
||||
- Archivierung statt Löschung (17.1.4)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
# M076 — Automation: Aktion-Registry + Steuerungs-Bausteine
|
||||
|
||||
**Block:** Block 4 · Modul 17
|
||||
**Pflichtenheft-Quelle:** block4.md Abschnitt 17.3
|
||||
|
||||
## Ziel
|
||||
Registry aller Phase-1-Aktionen (CRM, Leads, Sales, Projekte, Kommunikation, Aufgaben, KWP, externe HTTP, Steuerung, KI, Kalender, Dateien) + Steuerungs-Bausteine (Wartezeit, Verzweigung, parallel, Merge). KEINE Schleifen (Anti-Liste).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 17.3.1-17.3.12 — komplette Aktions-Liste
|
||||
- 17.3.9 — Schleifen ausdrücklich nicht erlaubt (Anti-Liste)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M075, M083 (KI-Provider für 17.3.10)
|
||||
- **Wird benötigt von:** M077-M082
|
||||
|
||||
## Out of Scope
|
||||
- Sub-Workflows / Loops → Anti-Liste, Phase 2
|
||||
- Custom-JS-Expressions → Anti-Liste, Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
Test-Automation: Auslöser → Bedingung → Email senden → Wartezeit 1h → Aufgabe anlegen funktioniert; Schleifen-Versuch in Editor abgelehnt.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Aktion-Interface mit Idempotency-Key (M007)
|
||||
- Steuerungs-Bausteine als spezielle „Aktion"-Subtypen
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M077 — Automation: Bedingungen
|
||||
|
||||
**Block:** Block 4 · Modul 17
|
||||
**Pflichtenheft-Quelle:** block4.md Abschnitt 17.4
|
||||
|
||||
## Ziel
|
||||
Bedingungs-Engine: Feld-Vergleich, Schlagwort, Tageszeit/Wochentag, Gruppen-Mitgliedschaft. Phase 1 ohne Custom-JS.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 17.4.1-17.4.4 — alle erlaubten Bedingungen
|
||||
- 17.4.5 — Custom-JS Phase 2 ausgeschlossen
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M075, M076
|
||||
- **Wird benötigt von:** M078
|
||||
|
||||
## Erfolgskriterium
|
||||
Test: „Volumen > 10000 EUR UND Schlagwort = ‚VIP'" greift korrekt; Bedingung wertet Pre-Save aus.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- AND/OR-Kombinatoren mit Klammer-Logik
|
||||
- Type-safe Feld-Picker (kennt Auslöser-Felder)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# M078 — Automation: Visueller Editor
|
||||
|
||||
**Block:** Block 4 · Modul 17
|
||||
**Pflichtenheft-Quelle:** block4.md Abschnitt 17.5
|
||||
|
||||
## Ziel
|
||||
xyflow-basierter Editor mit Knoten/Verbindungen, Mini-Map, Zoom, Undo/Redo, Konfigurations-Panel pro Knoten, Pre-Save-Validierung mit Klartext-Hinweisen, Pflicht-Aktivierung als separater Schritt.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 17.5 — alle Punkte
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M075-M077, M015 (UI-Layer)
|
||||
- **Wird benötigt von:** M079, M086 (KI-Sprache → Editor füllt)
|
||||
|
||||
## Out of Scope
|
||||
- KI-Erstellung → M086
|
||||
- Test-Lauf → M079
|
||||
|
||||
## Erfolgskriterium
|
||||
Editor-User baut Wenn-Dann-Flow per Drag&Drop; Pre-Save-Validator listet alle Probleme (17.5.6); Aktivierung explizit (17.5.7).
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- `@xyflow/react` bereits in Boilerplate-Deps
|
||||
- Knoten-Label mit Klartext (17.5.4)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M079 — Automation: Test-Lauf + Schwellenwert-Vorschau
|
||||
|
||||
**Block:** Block 4 · Modul 17
|
||||
**Pflichtenheft-Quelle:** block4.md Abschnitt 17.7 (Bauprinzip A.10)
|
||||
|
||||
## Ziel
|
||||
Test-Lauf-Simulation ohne echte Wirkung. Schwellenwert-Pflicht-Vorschau bei >100 Datensätzen mit Empfänger-Sample.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 17.7.1 — Test-Lauf
|
||||
- 17.7.2 — Schwellenwert-Vorschau (mandant-konfigurierbar) mit erste-5-Empfänger
|
||||
- A.10.1 — KI-erzeugte Automation immer erst Vorschau
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M075-M078
|
||||
- **Wird benötigt von:** M080, M086
|
||||
|
||||
## Erfolgskriterium
|
||||
Test-Lauf zeigt Schritt-für-Schritt Klartext („Email würde gesendet an X mit Betreff Y"); >100-Empfänger-Lauf erfordert explizite Bestätigung.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Dry-run-Mode ohne echten Aktion-Aufruf (Mock-Adapter)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
# M080 — Automation: 24h-Undo-Fenster + Reversibilität
|
||||
|
||||
**Block:** Block 4 · Modul 17
|
||||
**Pflichtenheft-Quelle:** block4.md Abschnitt 17.7.3-17.7.5 (Bauprinzip A.10.2)
|
||||
|
||||
## Ziel
|
||||
Jede Ausführung 24h rückgängig machbar. Reversibel: angelegte Datensätze, Status-Änderungen, Tag-Änderungen. Email-Versand nicht zurückziehbar, aber Empfänger-Liste sichtbar.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 17.7.3 — 24h-Fenster
|
||||
- 17.7.4 — Reversibilitäts-Liste
|
||||
- 17.7.5 — Mehrfach-Bestätigung + Audit
|
||||
- A.10.2 — 24h-Rückgängig-Fenster generell
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M075-M079, M001
|
||||
- **Wird benötigt von:** M081
|
||||
|
||||
## Erfolgskriterium
|
||||
Test-Run-Wirkung: 50 Datensätze angelegt → Undo binnen 24h löscht sie; nach 24h Undo-Knopf weg.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Undo-Token pro Run mit Snapshot der Auswirkungen
|
||||
- BullMQ-delayed Cleanup-Job nach 24h
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# M081 — Automation: Schleifen-Schutz + Webhook-Sturm + Anomalie
|
||||
|
||||
**Block:** Block 4 · Modul 17
|
||||
**Pflichtenheft-Quelle:** block4.md Abschnitt 17.8 (Bauprinzipien A.16, A.17)
|
||||
|
||||
## Ziel
|
||||
- Webhook-Sturm-Schutz: Hard-Limit 1000/h pro Mandant + Anomalie-Erkennung (10x Threshold)
|
||||
- Schleifen-Schutz: max 5 Auto-Trigger pro Datensatz/Min, Pre-Save-Graph-Analyse
|
||||
- Halbe-Ausführung: Idempotenz pro Schritt + Resume-from-failed-step + Backoff (1m/5m/15m/1h/6h/24h)
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 17.8.1-17.8.3 — alle drei Schutz-Mechanismen mit Klartext-Beispielen
|
||||
- A.16, A.17 — Querschnitt-Bezug
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M007 (Idempotenz), M010 (Webhook-Schutz Apps-Engine), M075-M078
|
||||
- **Wird benötigt von:** M082
|
||||
|
||||
## Erfolgskriterium
|
||||
Stress-Test: 1500 Webhooks/h → 500 verworfen + Notification; Schleifen-Detection blockt vor Speichern; halbe Ausführung resumed ab Schritt 4.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Klartext aus 17.8 (Pflichtenheft) übernehmen
|
||||
- Anomalie-Detector Rolling-Window
|
||||
- Backoff-Strategie als BullMQ-Retry-Config
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M082 — Automation: Klartext-Logs + Re-Run + Trigger-Volumen-Metering
|
||||
|
||||
**Block:** Block 4 · Modul 17
|
||||
**Pflichtenheft-Quelle:** block4.md Abschnitte 17.9 + Pricing-Vorbereitung
|
||||
|
||||
## Ziel
|
||||
Pro Run Klartext-Detail (Schritte, Dauer, Eingabe/Ausgabe, Fehler in Klartext). Manueller Re-Run + Undo aus Log. Trigger-Volumen pro Mandant/Stunde (Pricing-Vorbereitung, Limits später per Konfiguration).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 17.9 — Logs (Beispiel-Texte 17.9.3)
|
||||
- Anhang H.1.1 — Trigger-Volumen-Metering vorbereitet
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M075-M081
|
||||
- **Wird benötigt von:** M156 (Pay-as-you-go)
|
||||
|
||||
## Erfolgskriterium
|
||||
Run-Detail zeigt Schritt-Liste mit Dauer + Status; Re-Run aus Log funktioniert; Volumen-Counter sichtbar im Plattform-Admin.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Run-Log als unveränderlicher Stream
|
||||
- Klartext-Beispiele aus 17.9.3
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,87 @@
|
||||
# M089 — KWP-API-Connector (REST/OAuth über Apps-Engine)
|
||||
|
||||
**Block:** Block 4 · Modul 19
|
||||
**Pflichtenheft-Quelle:** block4.md Modul 19 + Bauprinzip A.18 · **Re-Cut 2026-06-04 (KWP-API), siehe `docs/milestones/M19-KWP-API-RECUT.md`**
|
||||
|
||||
## Ziel
|
||||
First-Party-Connector für die offizielle **KWP-REST-API**, aufgesetzt auf das M33a-Adapter-Interface. Eine `App{type:"kwp"}` + eine `DataConnection{type:"rest-api"|"oauth2"}` pro KWP-Server; API-Credentials verschlüsselt in `DataConnection.config` (Per-Tenant-DEK, AD-8). Ausgehende Calls via `adapterFetch()` (HTTPS-only, SSRF-Guard). Implementiert `connect / disconnect / validateConnection / syncPull / syncPush / handleWebhook`.
|
||||
|
||||
## Was sich durch die KWP-API ändert (Re-Cut)
|
||||
- **Der ursprüngliche Windows-Client (`kwpsync.exe` + NSSM + MSSQL-Direktzugriff + DPAPI + Auto-Update) entfällt komplett.** Kein externes Programm mehr — der Connector lebt im Monorepo (`app/domain/integrations/kwp/**`).
|
||||
- KWP wird ein **regulärer `rest-api`-Adapter** statt `windows_client`-Sonderweg; passt direkt ins `appsEngine.prisma`-Muster.
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M008–M010 (M33a Adapter-Interface — `connect/syncPull/syncPush/...`, harte Vorbedingung); AD-8 (Per-Tenant-DEK)
|
||||
- **Offen/blockierend:** konkreter **KWP-API-Vertrag** (Auth, Endpoints, Rate-Limits, Webhooks, Versionierung) — vor Detail-Planung mit KWP klären (siehe RECUT-Doku)
|
||||
- **Wird benötigt von:** M090–M095
|
||||
|
||||
## Out of Scope
|
||||
- `kwpsync.exe` / Windows-Service / NSSM / MSSQL-Direktzugriff (durch API obsolet)
|
||||
- Andere ERPs (Taifun, TopKontor) → Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
KWP-App via Setup verbunden; `validateConnection` liefert grün; Test-`syncPull` liefert einen KWP-Datensatz; Test-`syncPush` schreibt einen Datensatz via API nach KWP; alles als `AppSyncRun`/`AppSyncItem` protokolliert.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Connector als reines Domain-Modul (`app/domain/integrations/kwp/**`), Layer-Trennung (AGENTS.md)
|
||||
- `appsEngine.prisma`-Modelle nutzen; KWP-spezifische Modelle in eigenem `prisma/schema/kwp.prisma`
|
||||
- Mapping HiveGrid↔KWP via `AppSyncItem`; Idempotenz via `IdempotencyKey`
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
# M090 — KWP-API Connection-Health
|
||||
|
||||
**Block:** Block 4 · Modul 19
|
||||
**Pflichtenheft-Quelle:** block4.md Modul 19 + Bauprinzip A.18 · **Re-Cut 2026-06-04 (KWP-API)**
|
||||
|
||||
## Ziel
|
||||
Verbindungs-Gesundheit der KWP-API über den generischen M33a-Health-Probe (`validateConnection`-Call im Intervall) statt eines Client-Heartbeats. Status nach `AdapterStatus` (aktiv/eingeschränkt/defekt). Bei `defekt`: Alarm an Plattform-Admin + Mandanten-Admin (Geerkens).
|
||||
|
||||
## Was sich durch die KWP-API ändert (Re-Cut)
|
||||
- **Stark vereinfacht:** Client-Heartbeat (5 Min), 15-Min-Watchdog und Auto-Restart entfallen (kein lokaler Client mehr). Ersetzt durch periodischen Health-Call der Cloud an die KWP-API.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.18.1-A.18.3 (sinngemäß auf API-Health übertragen)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M089, M011 (Notifications)
|
||||
- **Wird benötigt von:** M091
|
||||
|
||||
## Erfolgskriterium
|
||||
Health-Status pro KWP-Connection sichtbar im Plattform-Admin; simulierter API-Ausfall setzt Status auf `defekt` und löst Push + Email aus; Erholung sendet Klartext-Bestätigung.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Nutzt `foundation/adapters` (`AdapterStatus`) + `notify()`; Probe-Intervalle aktiv 5min / eingeschränkt 1min / defekt 15min (M33a)
|
||||
- Health-Cron nach Muster `apps/worker/.../dsgvo-grace-cron.ts`
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
# M091 — KWP-Push-Queue + Replay (Cloud-Outbox)
|
||||
|
||||
**Block:** Block 4 · Modul 19
|
||||
**Pflichtenheft-Quelle:** block4.md Modul 19 + Bauprinzip A.19 · **Re-Cut 2026-06-04 (KWP-API)**
|
||||
|
||||
## Ziel
|
||||
Push-Operationen HiveGrid→KWP laufen über die transaktionale **Cloud-Outbox** (`kwp.push.*`-Prefix) + `@toolctrl/queue`. Bei KWP-API-Ausfall: Retry mit Backoff; bei Wiederverbindung chronologisches **Rate-Limited-Replay (max 100 Ops/Min)** mit sichtbarem Fortschritt (SSE).
|
||||
|
||||
## Was sich durch die KWP-API ändert (Re-Cut)
|
||||
- **Vereinfacht:** Die lokale SQLite-Queue im Client entfällt — es gibt nur noch **eine** Cloud-Queue (Outbox). Kein Zwei-Layer-Resilienz-Konstrukt mehr.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.19.1-A.19.3
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M089, M090
|
||||
- **Wird benötigt von:** M092, M093
|
||||
|
||||
## Erfolgskriterium
|
||||
Simulierter 6h-KWP-API-Ausfall → Push-Ops sammeln sich in der Outbox; bei Erholung Replay in chronologischer Reihenfolge mit Rate-Limit + Fortschrittsanzeige; Konflikte zeigen Klartext-Auflösung (M093).
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Outbox-Prefix-Routing (`kwp.push.*`) in `apps/worker/src/outbox/event-router.ts`; Queue-Name in `packages/queue/src/names.ts` registrieren
|
||||
- Idempotenz via `buildIdempotentJobId()` + `IdempotencyKey`
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
# M092 — KWP-API-Contract-Sentinel
|
||||
|
||||
**Block:** Block 4 · Modul 19
|
||||
**Pflichtenheft-Quelle:** block4.md Modul 19 + Bauprinzip A.11 · **Re-Cut 2026-06-04 (KWP-API)**
|
||||
|
||||
## Ziel
|
||||
Statt MSSQL-Schema-Drift jetzt **API-Vertrags-/Versions-Überwachung**: jede KWP-API-Response wird gegen ein erwartetes zod-Schema validiert; bei Vertragsbruch (unerwartete Felder/Typen, API-Version-Bump) → Sync **automatisch pausiert** + Alarm an **Plattform-Admin zuerst** (vor Geerkens).
|
||||
|
||||
## Was sich durch die KWP-API ändert (Re-Cut)
|
||||
- **Vereinfacht bis ggf. integrierbar:** Bei stabiler, versionierter API ändert KWP das Schema nicht mehr „still". Der tägliche MSSQL-Snapshot+Hash-Diff entfällt; übrig bleibt eine laufende zod-Response-Validierung + Versions-Check. Ob eigenständiges Milestone oder Teil des M089-Connectors hängt vom KWP-API-Versionierungs-Modell ab (offen).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.11.1-A.11.2
|
||||
- 33a.6 — Schema-/Contract-Drift generell
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M089-M091, M011 (Notifications)
|
||||
- **Offen:** KWP-API-Versionierungs-/Changelog-Modell (klären) — entscheidet den Umfang
|
||||
- **Wird benötigt von:** stabiler Geerkens-Betrieb
|
||||
|
||||
## Erfolgskriterium
|
||||
Eine bewusst veränderte/unerwartete API-Response (Feld umbenannt) wird von der zod-Validierung erkannt; Sync pausiert; Plattform-Admin erhält Push vor Geerkens es bemerkt; Mandant sieht Klartext „Wir wurden informiert".
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- zod-Schemas pro KWP-Endpoint; `KwpApiContractSnapshot` (API-Version + Schema-Fingerprint) statt MSSQL-Snapshot
|
||||
- Auto-Pause über M33a-Status (`degraded`) + `notify()` an Plattform-Admin zuerst, dann Mandant
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# M093 — KWP: Konflikt-Auflösung „KWP gewinnt" [N14]
|
||||
|
||||
**Block:** Block 4 · Modul 19
|
||||
**Pflichtenheft-Quelle:** block4.md Modul 19.6 + [N14, 09.05.2026] + Bauprinzip A.15 · **Re-Cut 2026-06-04: inhaltlich unverändert**
|
||||
|
||||
## Ziel
|
||||
Bei Versions-Konflikt KWP↔HiveGrid: Default „KWP gewinnt immer" (statt Last-Write-Wins). Diff-View für manuelle Auflösung. Klartext-Notification mit Restore-Knopf für überschriebenen User.
|
||||
|
||||
## Was sich durch die KWP-API ändert (Re-Cut)
|
||||
- **Unverändert** — transport-unabhängige Domain-Regel. Einzige Anpassung: Konflikt-Erkennung läuft über das `version_hash`/`last_modified`-Feld der **API-Response** statt über ein MSSQL-Feld; Restore des überschriebenen Stands via `AppSyncItem.rolledBackData`.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- A.15.1-A.15.2 — Optimistic Locking + Diff-View, Last-Write-mit-Sichtbarkeit
|
||||
- M19.6 + [N14] — KWP-spezifischer Default „KWP gewinnt"
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M089-M092
|
||||
- **Wird benötigt von:** alle Module mit KWP-Schreib-Pfad (M064 Sales-Pipeline, M066 Auftrag, M067 Plantafel)
|
||||
|
||||
## Erfolgskriterium
|
||||
Sandra ändert Auftrag in KWP, Mandanten-Mitarbeiter ändert parallel in HiveGrid; KWP-Wert gewinnt; Mitarbeiter sieht Klartext-Notification + Restore.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- `version_hash` aus KWP-API-Response je Datensatz; Restore aus `AppSyncItem.rolledBackData`
|
||||
- Diff-View-Component reusable (auch für M092/M094)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# M094 — KWP: Bidirektionale Plantafel-Sync [N10]
|
||||
|
||||
**Block:** Block 4 · Modul 19
|
||||
**Pflichtenheft-Quelle:** block4.md M19 + [N10, 09.05.2026] + M04.6.14 · **Re-Cut 2026-06-04 (KWP-API)**
|
||||
|
||||
## Ziel
|
||||
Plantafel-Änderungen bidirektional: HiveGrid→KWP via API-Call (`syncPush`), KWP→HiveGrid via Webhook (`handleWebhook`) bzw. Cron-Pull. Konflikt-Default „KWP gewinnt" (siehe M093).
|
||||
|
||||
## Was sich durch die KWP-API ändert (Re-Cut)
|
||||
- **Vereinfacht:** Kein `kwpsync.exe`-Schreibpfad in MSSQL mehr. Bietet die KWP-API Webhooks, wird **Trigger-basierter Pull Phase-1-fähig** (statt Phase 2); sonst Cron-Pull mit dokumentiertem Intervall.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- M04.6.14 + [N10] — bidirektional, KWP gewinnt bei Konflikt
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M089-M093, M067 (Plantafel-Modul)
|
||||
- **Offen:** KWP-API muss Plantafel-Endpoints + idealerweise Webhooks bieten (klären)
|
||||
- **Wird benötigt von:** Geerkens-Plantafel-Workflow
|
||||
|
||||
## Erfolgskriterium
|
||||
Plantafel-Move in HiveGrid landet in KWP <30 Sek; KWP-Änderung erscheint in HiveGrid <30 Sek (Webhook) bzw. zum nächsten Pull; gleichzeitige Konflikte werden mit „KWP gewinnt" aufgelöst.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- HiveGrid→KWP via `syncPush`/`adapterFetch`; KWP→HiveGrid via `handleWebhook` (signiert) oder Cron-`syncPull`
|
||||
- Fällt KWP-Webhook weg → Pull-Intervall + Latenz-Trade-off dokumentieren
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,87 @@
|
||||
# M095 — KWP: Dokumenten-Archiv-Sync KWP→HiveGrid [N5]
|
||||
|
||||
**Block:** Block 4 · Modul 19
|
||||
**Pflichtenheft-Quelle:** block4.md M19.2.5 + M23.9.7 + [N5, 09.05.2026] · **Re-Cut 2026-06-04 (KWP-API)**
|
||||
|
||||
## Ziel
|
||||
KWP-Kunden- und Projekt-Archiv-Struktur einseitig (KWP → HiveGrid) gespiegelt über den **KWP-API-Dokumenten-Endpoint**; Ablage in `@toolctrl/storage` (Scaleway-S3), read-only lesbar in HiveGrid. Quelle bleibt KWP.
|
||||
|
||||
## Was sich durch die KWP-API ändert (Re-Cut)
|
||||
- **Vereinfacht:** Kein lokaler Dateizugriff via Client. Dokumente werden über die API gelistet + heruntergeladen und in S3 abgelegt; inkrementell (nur neue/geänderte).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- M19.2.5 + M23.9.7 + [N5] — Dokumenten-Archiv-Sync, einseitig
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M089-M093, M052-M055 (Dateien-Modul)
|
||||
- **Offen:** KWP-API muss Dokumenten-Listing + Download bieten (klären)
|
||||
- **Wird benötigt von:** M066 (Auftrag-CRUD mit Archiv)
|
||||
|
||||
## Out of Scope
|
||||
- Bidirektionaler Datei-Sync (HiveGrid → KWP)
|
||||
|
||||
## Erfolgskriterium
|
||||
KWP-Datei „Auftrag_42/Foto.jpg" erscheint in HiveGrid-Auftrag-Archiv-Sicht <2 Min nach Upload in KWP; Schreibversuch in HiveGrid lehnt ab mit Klartext.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- API-Dokumenten-Listing + Download → `@toolctrl/storage` (Signed-URLs); `KwpDocument`-Mapping (`direction=downloaded_from_kwp`)
|
||||
- Inkrementeller Sync (Cursor/seit-Datum); „in KWP gelöscht"-Badge
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
# M096 — Email-Inbox: Gmail-OAuth-Integration via Apps-Engine
|
||||
|
||||
**Block:** Block 5 · Modul 9
|
||||
**Pflichtenheft-Quelle:** `_bmad-output/pflichtenheft/blocks/block5.md` Abschnitte 9.1, 9.5, 9.4
|
||||
|
||||
## Ziel
|
||||
Gmail (inkl. Workspace) und Microsoft Outlook/365 OAuth-Anbindung pro Mitarbeiter (Mehrfach-Postfach). Standard-Postfach-Markierung. Einmalige Sende-Domain-Verifikation pro Mandant (DKIM/SPF/DMARC mit Auto-Probe alle 5 Min, 7-Tage-Timeout).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 9.1 — Gmail + Outlook in Phase 1; andere IMAP/T-Online/GMX → Phase 2 (9.9.1)
|
||||
- 9.4 — Sende-Domain-Verifikation (DKIM/SPF/DMARC)
|
||||
- 9.5 — Mailbox-Sync (Push, 90 Tage Initial-Import, Token-Refresh, Watchdog 4h)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M008-M010 (Apps-Engine), M002 (Klartext)
|
||||
- **Wird benötigt von:** M097-M099, M100 (Marketing-Versand braucht verifizierte Domain)
|
||||
|
||||
## Out of Scope
|
||||
- Andere Email-Provider → Phase 2
|
||||
|
||||
## Erfolgskriterium
|
||||
Gmail-OAuth-Setup in <2 Min; DNS-Verifikation findet Einträge automatisch; Token-Refresh läuft monatelang stabil.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Adapter via Apps-Engine (M008)
|
||||
- Pub/Sub für Push-Sync, Polling-Watchdog als Sicherheitsnetz (9.5.5)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M097 — Email-Inbox: Sync + Inbox-UI + Threading + Auto-Verknüpfung
|
||||
|
||||
**Block:** Block 5 · Modul 9
|
||||
**Pflichtenheft-Quelle:** block5.md Abschnitte 9.2, 9.3
|
||||
|
||||
## Ziel
|
||||
Inbox mit Listen-Ansicht (Filter: Postfach/Eingang-Ausgang/Lese-Status/Verknüpfung/Datum/Anhang), Volltext-Suche, Detail mit Thread, Tracking-Pixel-Schutz (Bilder erst nach Klick), Mark-as-Read-Sync zurück zum Provider. Auto-Verknüpfung (Email-Adresse, Betreff-Kürzel `[Deal #X]`, Heuristik bei genau-einem-offenen-Deal).
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 9.2 — Inbox-Sicht
|
||||
- 9.3 — Auto-Verknüpfung
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M096, M042 (Kontakt für Match), M060/M066 (Deal/Auftrag)
|
||||
- **Wird benötigt von:** M098, M099, M045 (Activity-Stream)
|
||||
|
||||
## Erfolgskriterium
|
||||
Mail von bekanntem Kontakt → automatisch verknüpft; Mail mit `[Deal #42]` → automatisch zum Deal; manuelle Override hält stand (9.3.4).
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Bilder-Lade-Schutz CSP-basiert
|
||||
- Newsletter/Bulk via List-Header-Detection (9.3.6)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M098 — Email-Versand + Vorlagen + Variable-Resolution
|
||||
|
||||
**Block:** Block 5 · Modul 9
|
||||
**Pflichtenheft-Quelle:** block5.md Abschnitt 9.7
|
||||
|
||||
## Ziel
|
||||
Versand aus Kontakt-/Deal-/Projekt-Detail oder Inbox (Antwort/Weiterleiten). Editor mit Formatierung + Anhängen (≤25 MB). Mehrfach-Postfach-Auswahl. Native Versand über Provider (Mail erscheint in Provider-Gesendet-Ordner). Optional BCC-Logging.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 9.7 — Versand
|
||||
- 9.6 — Quotenschutz (1B/Tag Gmail, 10K/Tag Outlook, Drosselung)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M096, M097
|
||||
- **Wird benötigt von:** M092 (Calendar-Bestätigungen), M122 (Booking-Bestätigung)
|
||||
|
||||
## Erfolgskriterium
|
||||
Mail aus Kontakt-Detail mit Vorlage + Variable `{{first_name}}` korrekt aufgelöst, an Empfänger zugestellt, im Gmail-Gesendet-Ordner sichtbar.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- TipTap-Editor (in Boilerplate-Deps)
|
||||
- Variable-Resolver mit Kontakt-Properties
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M099 — Email-Tracking + Delivery-Status + Bounces
|
||||
|
||||
**Block:** Block 5 · Modul 9 (sowie M10)
|
||||
**Pflichtenheft-Quelle:** block5.md Abschnitt 9.6 (transaktionale) + Modul 10.4-10.6 (Marketing)
|
||||
|
||||
## Ziel
|
||||
Delivery-Status pro Versand (zugestellt/bounced/spam-marked). Hard-/Soft-Bounce-Handling (Sperrliste-Auto-Add bei Hard-Bounce). Quoten-Schutz pro Provider.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 9.6 — Quoten + Bounces
|
||||
- 10.6 — Bounce-Handling Marketing
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M098
|
||||
- **Wird benötigt von:** M100-M104
|
||||
|
||||
## Erfolgskriterium
|
||||
Hard-Bounce setzt Adresse auf Sperrliste mit Klartext-Hinweis im Kontakt-Detail; Soft-Bounce 3× retry über 24h, dann wie Hard-Bounce.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Bounce-Webhook vom Provider
|
||||
- Sperrliste pro Mandant
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
# M100 — Email-Marketing: Editor (Block-Style)
|
||||
|
||||
**Block:** Block 5 · Modul 10
|
||||
**Pflichtenheft-Quelle:** block5.md Abschnitte 10.1, 10.4 (Pixel-Tracking-Hinweis)
|
||||
|
||||
## Ziel
|
||||
Kampagnen-Builder mit Schritten (Basis → Inhalt → Empfänger → Test → Versand-Zeit → Bestätigung). Personalisierungs-Platzhalter `{{first_name}}` etc. SHK-Standard-Templates. Vorschau Desktop+Mobile. Test-Mail an sich selbst.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 10.1 — Newsletter + Sequenzen (Sequenzen Phase 1 via Automation, 10.1.6)
|
||||
- 10.4.6 — Datenschutz-Hinweis Tracking-Pixel im Footer
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M096, M098, M158 (SHK-Standard-Templates)
|
||||
- **Wird benötigt von:** M101-M104
|
||||
|
||||
## Out of Scope
|
||||
- Drag-&-Drop-Builder → Phase 2 (10.11.5)
|
||||
- Bedingter Inhalt → Phase 2 (10.11.4)
|
||||
|
||||
## Erfolgskriterium
|
||||
Kampagne „Wartungs-Erinnerung" mit Template + Variablen erstellbar; Vorschau zeigt Desktop+Mobile mit Sample-Daten; Test-Mail kommt an.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- TipTap-Editor reuse
|
||||
- Spam-Score-Check vor Versand (10.9.3)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M101 — Email-Marketing: Segmente + Empfänger-Auswahl
|
||||
|
||||
**Block:** Block 5 · Modul 10
|
||||
**Pflichtenheft-Quelle:** block5.md Abschnitte 10.2, 10.7
|
||||
|
||||
## Ziel
|
||||
Segment-Filter (Tags, Lifecycle, Custom-Felder, Verantwortlicher, Erstellt-Datum, verknüpft mit Deal, Sprache) verschachtelt UND/ODER. Live-Empfänger-Anzahl + 50-Stichprobe. Statisch vs. dynamisch. Auto-Ausschluss (keine Einwilligung, abgemeldet, Sperrliste, archiviert) mit Klartext-Counter. DSGVO-Einwilligungs-Pflicht-Doku pro Kontakt.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 10.2 — Segmente
|
||||
- 10.7 — DSGVO-Einwilligungs-Pflicht (kritisch)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M042-M046, M100
|
||||
- **Wird benötigt von:** M102-M104
|
||||
|
||||
## Erfolgskriterium
|
||||
Segment „Wartungsvertrag-Kunden ohne Wartung > 365d" liefert Live-Anzahl; Versand-Bestätigung zeigt „X aus Y Empfängern werden ausgeschlossen (Abmeldung/Bounce/keine Einwilligung)".
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Filter-DSL als JSON
|
||||
- Double-Opt-In-Flow (10.7.3)
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,82 @@
|
||||
# M102 — Email-Marketing: Versand-Engine + DKIM/SPF + Frequenz-Schutz
|
||||
|
||||
**Block:** Block 5 · Modul 10
|
||||
**Pflichtenheft-Quelle:** block5.md Abschnitte 10.5, 10.7.5, 10.9
|
||||
|
||||
## Ziel
|
||||
Versand-Worker mit Tagebudget pro Plan (Cloud 10K, Cloud+ 50K, Trial 200), Frequenz-Schutz (max 5 Mails/Empfänger/Woche), Pflicht-Footer (Absender-Adresse, Abmelde-Link auto-injected falls vergessen). Domain-Reputation-Schutz.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 10.5 — Unsubscribe-Pflicht (Abmelde-Link auto-eingefügt)
|
||||
- 10.7.5 — Pflicht-Inhalte Footer
|
||||
- 10.9 — Tages-Limit + Frequenz + Spam-Score-Check
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M096 (Sende-Domain), M101, M007 (Idempotenz)
|
||||
- **Wird benötigt von:** M103, M104
|
||||
|
||||
## Erfolgskriterium
|
||||
Kampagne ohne Footer-Adresse → Versand blockiert mit Klartext (10.7.5 + 10.12.7); 5. Mail/Woche an Empfänger geblockt.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- BullMQ-Worker für Versand mit Drossel
|
||||
- Auto-Footer-Injection
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# M103 — Email-Marketing: Reporting (Open/Click + Klick-Karte + Pro-Empfänger)
|
||||
|
||||
**Block:** Block 5 · Modul 10
|
||||
**Pflichtenheft-Quelle:** block5.md Abschnitt 10.4
|
||||
|
||||
## Ziel
|
||||
Pro Kampagne: Versendet/Zugestellt/Hard-Bounce/Soft-Bounce/Geöffnet/Geklickt/Abgemeldet/Spam-Beschwerden + Quoten. Klick-Karte (Links nach Häufigkeit). Pro-Empfänger-Liste. Marketing-Engagement-Aggregat im Kontakt-Detail.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 10.4 — Tracking-Detail (manuelle A/B in Phase 1, Auto-A/B Phase 2)
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M099, M102
|
||||
- **Wird benötigt von:** Marketing-Workflow
|
||||
|
||||
## Out of Scope
|
||||
- Auto-A/B-Tests → Phase 2 (10.11.1)
|
||||
- Geräte/Geo/Heat-Map → Phase 2 (10.11.3)
|
||||
|
||||
## Erfolgskriterium
|
||||
Kampagne-Versand → Tracking-Pixel-Loads zählt Open; Click-Tracking via Redirect-Link; Aggregat im Kontakt zeigt Engagement-%.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Pixel-Endpoint für Open-Tracking
|
||||
- Redirect-Endpoint für Click-Tracking
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,81 @@
|
||||
# M104 — Email-Marketing: Unsubscribe + Bounce-Handling + Pflicht-Footer
|
||||
|
||||
**Block:** Block 5 · Modul 10
|
||||
**Pflichtenheft-Quelle:** block5.md Abschnitte 10.5, 10.6
|
||||
|
||||
## Ziel
|
||||
Public-Abmelde-Seite (kein Login), optionaler Grund + Feedback. Sperrliste pro Mandant (auch nach CRM-Lösch persistent). Ein-Klick-Abmeldung via Provider-Header. Spam-Beschwerden auto-Abmeldung.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 10.5 — Unsubscribe-Pflicht
|
||||
- 10.6 — Bounce + Spam-Beschwerden
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M102, M099
|
||||
- **Wird benötigt von:** Marketing-Workflow
|
||||
|
||||
## Erfolgskriterium
|
||||
Klick auf Abmelde-Link → Public-Page → Bestätigung → Adresse auf Sperrliste; Spam-Beschwerde via Provider-Webhook → Auto-Abmeldung mit Activity-Eintrag.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Public-Route (kein Login, Token-basiert)
|
||||
- List-Unsubscribe-Header für Provider-One-Click
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,80 @@
|
||||
# M105 — Telefonie: HalloPetra-Adapter [N16]
|
||||
|
||||
**Block:** Block 5 · Modul 12 [N16, 09.05.2026]
|
||||
**Pflichtenheft-Quelle:** block5.md Abschnitt 12.1.7
|
||||
|
||||
## Ziel
|
||||
HalloPetra-Anbindung pro Mandant (analog AirCall). Auto-Mitarbeiter-Zuordnung über Email. Eingehende Anrufe + verpasste Anrufe + Mitschnitt-Link + HalloPetra-Notiz im Activity-Stream. Click-to-Call wo API-fähig, sonst tel:-Fallback. HalloPetra-Sprach-Bot/Vorqualifikations-Tags als Lead-Eintrag.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 12.1.7 — alle Punkte [N16]
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M008-M010 (Apps-Engine), M042
|
||||
- **Wird benötigt von:** M107-M109
|
||||
|
||||
## Erfolgskriterium
|
||||
HalloPetra-Anruf-Eingang erscheint in HiveGrid mit Anrufer-Nummer + Mitschnitt-Link; Vorqualifikations-Tag als Activity-Eintrag.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- Adapter via Apps-Engine
|
||||
- Click-to-Call-Detection mit Fallback
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
@@ -0,0 +1,82 @@
|
||||
# M106 — Telefonie: AirCall-Adapter
|
||||
|
||||
**Block:** Block 5 · Modul 12
|
||||
**Pflichtenheft-Quelle:** block5.md Abschnitte 12.1.1-12.1.6
|
||||
|
||||
## Ziel
|
||||
AirCall-OAuth-Anbindung einmalig pro Mandant. Auto-Mitarbeiter-Zuordnung über Email mit manueller Korrektur. „Verbindung testen". Token-Refresh.
|
||||
|
||||
## Pflichtenheft-Bezug
|
||||
- 12.1.1-12.1.6 — alle Punkte
|
||||
|
||||
## Abhängigkeiten
|
||||
- **Vorbedingung:** M008-M010
|
||||
- **Wird benötigt von:** M107-M109
|
||||
|
||||
## Out of Scope
|
||||
- Sipgate, Auerswald → Phase 2 (12.10.1)
|
||||
|
||||
## Erfolgskriterium
|
||||
AirCall-OAuth-Flow grün; X von Y Mitarbeitern auto-zugeordnet, Rest manuell; Verbindungs-Test schlägt Verbindungsabbruch erkennbar an.
|
||||
|
||||
## Hinweise für Slice-Planung
|
||||
- AirCall-API über Apps-Engine
|
||||
|
||||
|
||||
---
|
||||
|
||||
## Definition of Done — verbindlich (siehe `AGENTS.md` + `docs/INTEGRATION-CONTRACTS.md`)
|
||||
|
||||
Dieses Milestone gilt **nur dann als erledigt**, wenn alle Punkte wahr sind. Bei Verstoß: PR-Block.
|
||||
|
||||
### Erreichbarkeit
|
||||
- [ ] **Sidebar-Eintrag** in `packages/ui-hivegrid/src/app-shell/sidebar.config.ts` mit Permission-Gate (oder explizit dokumentiert, warum nur Inline-Verlinkung) — Gruppe gemäß `docs/INTEGRATION-CONTRACTS.md` §1
|
||||
- [ ] **Route** unter korrektem URL-Pattern (INTEGRATION-CONTRACTS §3)
|
||||
- [ ] **Breadcrumb** für Detail-Routes (§4)
|
||||
- [ ] **Mobile-Tab-Bar-Eintrag** falls mobile-relevant (§13)
|
||||
- [ ] **Customer-Portal-Sichtbarkeit** explizit konfiguriert (§14)
|
||||
|
||||
### Querschnitt-Wiring
|
||||
- [ ] **Audit** läuft (auto via M001 oder manuell)
|
||||
- [ ] **Activity-Stream** via `logActivity` bei relevanter Aktion (M045)
|
||||
- [ ] **Notifications** via `notify()` (M011), nicht direkt
|
||||
- [ ] **Search-Index** registriert in `indexed-entities.ts`, falls suchbar
|
||||
- [ ] **Permission-Filter** via `withTenantScope()` + `withPermission()` (M004)
|
||||
- [ ] **Feature-Flag-fähig** (M006) — Modul ohne Deploy abschaltbar
|
||||
|
||||
### Code-Layer-Disziplin (PR-Block)
|
||||
- [ ] Loader baut View-Model; UI-Component empfängt nur VM + Actions
|
||||
- [ ] Keine Prisma-/Server-Imports in `packages/ui-hivegrid/**`
|
||||
- [ ] Subframe-Output via Adapter, nicht direkt importiert
|
||||
- [ ] Alle UI-Texte als i18n-Keys (M003-Build-Lint blockt sonst)
|
||||
|
||||
### Tests
|
||||
- [ ] **Unit-Test** für VM-Builder mit Zod-Schema-Validierung
|
||||
- [ ] **Smoke-Test** `e2e/smoke/<modul>.spec.ts` (Login → Route → Hauptaktion → erwartetes UI)
|
||||
- [ ] **Hot-Swap-Drill** grün (Smoke-Test gegen `packages/ui-mock` aus M017)
|
||||
- [ ] **Visual-Regression-Snapshot** der Hauptansicht (M016)
|
||||
|
||||
### Klartext (User-facing)
|
||||
- [ ] Fehler-Texte aus M002-Catalog (kein HTTP-Code im UI)
|
||||
- [ ] Empty-State mit Klartext + nächster Aktion
|
||||
- [ ] Loading-State mit Klartext (kein leerer Spinner)
|
||||
- [ ] Permission-Denied → 404, nicht 403 (Bauprinzip A.5.3)
|
||||
|
||||
### Rollback-Pfad
|
||||
- [ ] **Forward-Only-DB-Migration** mit Inverse-SQL als Kommentar
|
||||
- [ ] **Atomic-Slice-Commits** (TC-Default)
|
||||
- [ ] **Feature-Flag** vorhanden, um das Modul ohne Deploy auszuschalten
|
||||
|
||||
---
|
||||
|
||||
## Klick-Pfad zum Prüfen (für User)
|
||||
|
||||
Wenn dieses Milestone fertig ist, prüft der User die Funktion über folgenden Pfad:
|
||||
|
||||
1. Login als geeigneter User-Typ (siehe Erfolgskriterium oben)
|
||||
2. Sidebar-Gruppe + Eintrag öffnen (gemäß INTEGRATION-CONTRACTS.md §1)
|
||||
3. Hauptaktion ausführen
|
||||
4. Erwartetes Ergebnis sichtbar (siehe Erfolgskriterium)
|
||||
|
||||
**Falls etwas nicht erreichbar ist:** Milestone ist trotz „grüner Tests" nicht fertig — siehe Erreichbarkeits-Checkliste oben.
|
||||
|
||||
Loaded 100 of 5784 files, more files were not shown because too many files have changed in this diff.
Show more
Reference in new issue
Block a user