Files
flat-pilot/docs/hauspilot-domain.md
Bastian Wagner e62673ac11 mvp
2026-07-20 09:01:36 +02:00

16 KiB
Raw Blame History

HausPilot-Fachmodule

MVP-Abschluss 2026-07

Neue Migration und Datenmodelle

1720000005000-AddMentionsAndReminders.ts ergänzt task_comment_mentions, reminder_deliveries und applied_project_templates. Eindeutige Constraints deduplizieren Benutzer pro Kommentar, Reminder-Schlüssel sowie Vorlagen je Projekt und Ziel. Die Tabellen referenzieren weiterhin ausschließlich bestehende Benutzer- und Projekt-UUIDs.

Listen-API

Räume, Aufgaben, Meilensteine, Ausgaben, Dokumente, Kommentare und Aktivitäten liefern serverseitig { items, page, pageSize, totalItems, totalPages }. pageSize ist auf 100 begrenzt. Filter enthalten stets projectId. Sortierfelder sind DTO-Whitelists und werden nie als frei übergebener SQL-Ausdruck ausgeführt. Aufgaben unterstützen Suchtext, mehrere Statuswerte, Priorität, Raum, Verantwortlichen, Kategorie, Datumsbereiche, überfällig, blockiert, nicht zugewiesen und „nur meine“. Ausgaben und Dokumente besitzen Zuordnungs- und Datumsfilter.

Neue gezielte Leseendpunkte sind GET /projects/:projectId/tasks/:taskId und GET /projects/:projectId/calendar?from=YYYY-MM-DD&to=YYYY-MM-DD. Die stabile Angular-Route /projekte/:projectId/aufgaben/:taskId enthält Stammdaten, Schnellstatus, Checkliste, Vorgänger und Nachfolger, Kommentare, Erwähnungen, Dokumente und den Aktivitätsauszug. Der Zeitplan bietet eine responsive Monats- und Agendaansicht ohne neue UI-Bibliothek und lädt nur den benötigten Zeitraum.

Vorlagen

Die unveränderlichen Systemvorlagen „Reihenhaus-Renovierung“, „Schlüsselübergabe“, „Renovierung eines Raums“ und „Umzug“ werden transaktional kopiert. Die Reihenhausvorlage enthält fünf Bereiche, 15 Räume, 13 Budgetkategorien, Meilensteine und allgemeine Aufgaben. Die Raumvorlage erzeugt 14 Aufgaben samt Abhängigkeitskette. applied_project_templates erkennt Wiederholungen je Projekt und Zielraum; erneute Anwendung verlangt confirmDuplicate. Fehler rollen alle Kopien und die Aktivität gemeinsam zurück.

Strukturierte Erwähnungen

Kommentare übertragen neben sichtbarem @Anzeigename eine validierte Liste stabiler Benutzer-UUIDs. Nur aktive Mitglieder desselben Projekts werden akzeptiert. Mehrfachnennungen werden dedupliziert, Selbst-Erwähnungen erzeugen keine Nachricht und beim Bearbeiten werden nur neu hinzugekommene Benutzer benachrichtigt. Die In-App-Nachricht verweist direkt auf Aufgabe und Kommentar.

Scheduler und Reminder

Der offizielle Nest-Scheduler führt den ReminderService standardmäßig alle 15 Minuten aus. Er erfasst bald fällige und überfällige Aufgaben, Meilensteine, überfällige offene Ausgaben sowie bald ablaufende Einladungen mit bekanntem Benutzer. Entfernte oder global deaktivierte Mitglieder erhalten nichts. reminder_deliveries.dedupe_key enthält Reminder-Art, Entität, Empfänger und Bezugsdatum; der Unique Constraint schützt auch parallele Läufe. Eine Datumsänderung erzeugt einen neuen fachlich relevanten Schlüssel.

  • REMINDER_INTERVAL_MS: mindestens 60.000, Standard 900.000
  • REMINDER_DUE_SOON_DAYS: Standard 3

Development-Seed

Nach Migrationen und mindestens einem vorhandenen aktiven SSO-Benutzer wird der ausschließlich explizite Seed gestartet:

npm run seed:development

Er erzeugt idempotent „Umzug Reihenhaus“ mit fünf Etagen, 15 Räumen, 30 Aufgaben, zehn Abhängigkeiten, 20 Checklistenpunkten, zehn Kommentaren, acht Meilensteinen, 13 Budgetkategorien, 15 Ausgaben, vier Dokumentmetadaten, 20 Aktivitäten, In-App-Benachrichtigungen und sofern vorhanden bis zu vier bestehende Benutzer in unterschiedlichen Rollen. Er legt weder Benutzer noch Passwörter an. In NODE_ENV=production verweigert er Ausführung und Reset. Der gezielte Reset entfernt nur das eindeutig markierte Seed-Projekt:

npm run seed:development -- --reset

Seed-Dokumente enthalten absichtlich nur Metadaten, keine fingierten Binärdateien.

Abhängigkeitssicherheit und Grenzen

Die produktiven Advisories wurden ohne Major-Upgrade geschlossen: @nestjs/swagger 11.4.6 und TypeORM 0.3.31 beheben die gemeldeten transitiven Risiken in js-yaml, lodash, path-to-regexp und TypeORM. npm audit --omit=dev meldet danach keine bekannte Schwachstelle. @nestjs/schedule 6.1.3 (MIT, Nest-10/11-kompatibel) ist die einzige neue Laufzeitabhängigkeit.

Der Scheduler läuft pro Backend-Instanz; der Datenbank-Constraint macht die Auslieferung mehrfach laufender Instanzen idempotent, ersetzt bei sehr großen Installationen jedoch kein verteiltes Job-Leasing. Komplexe Gantt-, Offline-, E-Mail- und externe Kalenderfunktionen bleiben außerhalb des MVP.

Ausgangsarchitektur und Wiederverwendung

Die Umsetzung erweitert die bestehende Angular-/NestJS-Anwendung. Globale Anmeldung, OIDC, serverseitige MySQL-Session, CSRF, PermissionsGuard, ProjectAccessService, ProjectMembershipEntity, NotificationsService und ProjectActivityEntity bleiben die einzigen Mechanismen für Identität, Projektzugriff, Benachrichtigungen und Aktivitäten. Es gibt keine zweite Benutzer-, Login-, Session- oder Projektverwaltung.

Die fachlichen Controller tragen weiterhin @RequirePermissions(Permission.ProjectsUse). Danach prüft ProjectAccessService die aktive Mitgliedschaft und die Projektrolle. Jede Unterentität wird zusätzlich mit der Kombination aus id und projectId geladen. Dadurch reicht weder eine gültige Anmeldung noch eine fremde Entitäts-ID zum Zugriff.

Datenmodell und Module

RenovationModule bündelt die eng zusammenhängende Renovierungsdomäne und besteht aus Controller, Service, Persistence-Repository, Dokumentablage und DTO-Validierung. Die Migration 1720000004000-AddRenovationDomain.ts ergänzt:

  • Gebäude, Etagen und Räume
  • Renovierungsaufgaben, Checklisten, Abhängigkeiten und Kommentare
  • Meilensteine
  • Budgetkategorien und Ausgaben
  • projektbezogene Dokumentmetadaten
  • Projektstatus, Währung und Gesamtbudget-Grundlage

Historische Benutzerbeziehungen verwenden die bestehende interne User-UUID. Beim Entfernen eines Mitglieds werden offene Zuweisungen in derselben Transaktion geleert; abgeschlossene und historische Beziehungen bleiben erhalten.

API

Die API liegt unter /api/projects/:projectId und stellt Listen sowie Create-/Patch-/Delete-Endpunkte für buildings, floors, rooms, tasks, milestones, budget-categories, expenses und documents bereit. Aufgaben besitzen zusätzlich checklist, dependencies und comments. Weitere gezielte Endpunkte sind:

  • GET /projects/:projectId/dashboard
  • GET /projects/:projectId/activities
  • GET /templates
  • POST /projects/:projectId/apply-template/:templateId
  • GET /projects/:projectId/documents/:id/download

Request-DTOs enthalten weder Ersteller noch handelnde Benutzer. Diese IDs stammen ausschließlich aus dem bestehenden Sessionkontext.

Rollen

  • Eigentümer und Projektadministratoren verwalten die gesamte Struktur, Budgets und Vorlagen.
  • Bearbeiter verwalten Räume, Aufgaben, Checklisten, Kommentare, Ausgaben und Dokumente.
  • Leser können ausschließlich lesen.

Budgetkategorien sind bewusst Eigentümern und Projektadministratoren vorbehalten, weil ihre Änderung den finanziellen Projektrahmen verändert. Globale SSO-Rollen erzeugen weiterhin keine Projektmitgliedschaft.

Fortschritt und Abhängigkeiten

Die einzige Fortschrittsberechnung liegt in renovation/progress.ts: Idee 0, geplant 10, beauftragt 25, in Arbeit 50, blockiert 25, Abnahme 90 und erledigt 100 Prozent. Entfallene Aufgaben werden ausgeschlossen. Das optionale positive Gewicht bildet einen gewichteten Mittelwert; ohne fachliches Gewicht wird 1 verwendet.

Die zentrale Zykluserkennung erweitert den gerichteten Graphen probeweise um die neue Kante und führt eine Tiefensuche mit visiting-/visited-Mengen aus. Selbstbezüge sowie direkte und indirekte Zyklen werden mit HTTP 409 abgewiesen. Eine Aufgabe ist blockiert, sobald ein zwingender Vorgänger nicht erledigt ist; der Start wird dann serverseitig verhindert.

Dashboard und Budget

Der Dashboard-Endpunkt berechnet aggregiert Gesamtfortschritt, offene, überfällige, blockierte, kritische, eigene und nicht zugewiesene Aufgaben, Raumstatus, nächste/gefährdete Meilensteine, aktive Mitglieder sowie geplante, tatsächliche, offene und bezahlte Kosten. Handlungsorientierte Hinweise werden serverseitig aus denselben Daten erzeugt.

Geldbeträge werden in MySQL als DECIMAL gespeichert und erst für Aggregationen explizit in Zahlen überführt. Stornierte Ausgaben fließen nicht in tatsächliche Kosten ein.

Optimistische Nebenläufigkeit

Gebäude, Etagen, Räume, Aufgaben, Meilensteine, Budgetkategorien, Ausgaben und Dokumentmetadaten besitzen eine Versionsnummer. Updates verwenden atomar WHERE id = ? AND project_id = ? AND version = ? und erhöhen die Version in derselben SQL-Anweisung. Ein veralteter Stand überschreibt daher keine neueren Daten und liefert HTTP 409. Angular zeigt dafür einen konkreten Konflikthinweis und führt keine verlustbehaftete automatische Zusammenführung durch.

Dokumentablage

Dateien werden nicht öffentlich ausgeliefert. Upload und Download laufen nach Projektzugriffsprüfung über das Backend. Erlaubt sind PDF, JPEG, PNG und WebP bis zum konfigurierten Limit. Endung, MIME-Typ und Dateisignatur müssen zusammenpassen; der Speichername ist eine zufällige UUID und Pfadbestandteile aus dem Client werden nie übernommen. Metadaten liegen in MySQL, Inhalte unter DOCUMENT_STORAGE_PATH.

Konfiguration:

  • DOCUMENT_STORAGE_PATH (Standard storage/documents)
  • DOCUMENT_MAX_FILE_SIZE_BYTES (Standard 10 MiB)

Für mehrere Backend-Instanzen muss der Pfad als gemeinsames, geschütztes Volume bereitgestellt werden. Virenscanning und objektbasierter Cloud-Speicher sind sinnvolle Produktionsausbaustufen.

Frontend

Der responsive Projektarbeitsbereich nutzt ausschließlich bestehende Design-Tokens und UI-Komponenten. Die horizontale, tastaturbedienbare Projektnavigation umfasst Übersicht, Räume, Aufgaben, Zeitplan, Budget, Dokumente, Aktivitäten und die bestehende Mitgliederseite. Listen wechseln auf kleinen Displays in Karten; Hauptaktionen benötigen kein Hover.

Vorlagen und Erweiterbarkeit

Systemvorlagen werden als unveränderliche Definitionen angeboten. Die Raumrenovierung kopiert Aufgaben und Abhängigkeiten; ein vorhandener Aufgabenbestand verlangt eine explizite Duplikatbestätigung. Die Servicegrenze ist für weitere transaktionale Vorlagen vorbereitet.

Spätere Module für Kartons/QR-Codes, Inventar, Lieferanten/Angebote, Materialmengen, Rechnungserkennung, KI-Planung, E-Mail-Erinnerungen und Kalenderintegration können über projectId, bestehende Mitgliedschaften, Dokumentreferenzen, Aktivitäten und Benachrichtigungen angebunden werden, ohne Authentifizierung oder Projektzugriff zu duplizieren.

Tests

Die Verhaltenstests decken insbesondere die gewichtete Fortschrittsberechnung, ausgeschlossene Aufgaben, direkte/indirekte Abhängigkeitszyklen, kombinierte Aufgabenfilter und den Concurrency-Hinweis ab. Bestehende Tests sichern SSO, Projektzugriff, Einladungen, Sessions und Benachrichtigungen weiterhin ab.

Frühere MVP-Grenzen

Die zuvor fehlenden Vorlagen, strukturierten Erwähnungen und deduplizierten Reminder wurden mit dem oben dokumentierten MVP-Abschluss umgesetzt. Eine Queue wurde dafür bewusst nicht eingeführt.

Möbel- und Einrichtungsplanung

AG-Grid-Arbeitsoberfläche

Die Möbelverwaltung nutzt ag-grid-angular und ag-grid-community 36.0.1 (MIT, Community Edition). Registriert wird ausschließlich AllCommunityModule. Enterprise-Funktionen wie Row Grouping und Master/Detail werden weder importiert noch vorausgesetzt. Bedarfe, Alternativen, Bestellungen und Szenarien sind getrennte Grid-Ansichten; die vorhandenen Formulare bleiben für die vollständige Detailbearbeitung zuständig.

Listen verwenden die bestehende Page-Antwort (items, page, pageSize, totalItems, totalPages). Bedarfe unterstützen zusätzlich openDecision und overBudget; die projektweite Alternativenliste unterstützt roomId, requirementId, status, availability, favorite, selected, ordered und delayed. Sortierfelder werden im Service gegen Positivlisten geprüft. Bedarfsantworten enthalten aggregierte Optionen, Preise, Budgetabweichung, Bestellstatus und Lieferdatum. Die Repository-Abfragen laden Optionen gebündelt für die aktuelle Seite.

Inline-Änderungen senden die vorhandene Versionsnummer. Bei Fehlern wird der alte Zellwert wiederhergestellt; bei HTTP 409 wird der Serverstand neu geladen und der Konflikt sichtbar gemeldet. Favorit und Auswahl verwenden die bestehenden Fachendpunkte. Leser erhalten keine Editoren; die serverseitige Projektberechtigung bleibt verbindlich.

Spaltenzustand wird ohne Fachdaten lokal unter Benutzer-, Projekt- und Ansichtsschlüssel gespeichert. Die Suche wird um 300 ms entprellt, Row-IDs sind stabile Datenbank-IDs und CSV-Export nutzt die Community-Funktion. Auf kleinen Displays gelten eine reduzierte Höhe und die vorhandene Dialogbearbeitung für komplexe Eingaben.

Die Möbelplanung ist Bestandteil des vorhandenen RenovationModule und verwendet dessen ProjectAccessService, Dokumentablage, Ausgaben, Aktivitäten und Benachrichtigungen. Ein FurnitureRequirement beschreibt den Bedarf eines Raums; konkrete Produkte werden als FurnitureOption gespeichert. FurnitureScenario und FurnitureScenarioSelection kombinieren höchstens eine Alternative je Bedarf zu vergleichbaren Einrichtungsvarianten.

Preis- und Kostenregeln

Der geplante Gesamtpreis lautet Einzelpreis × Menge + Versand + Zusatzkosten Rabatt. Bei vorhandenem Mobiliar entfallen Anschaffungskosten; Umzug und Aufbereitung werden dennoch berücksichtigt. Alle persistierten Geldwerte sind DECIMAL(13,2) und werden im Backend als Strings verarbeitet; die zentrale Berechnung in furniture-pricing.ts rechnet in Cent. Planwerte stammen aus der ausgewählten Alternative bzw. einem Szenario. Ist-Kosten stammen ausschließlich aus nicht stornierten, über furniture_option_id verknüpften Ausgaben. Damit wird eine Bestellung nicht zugleich als Produktpreis und Ausgabe doppelt gezählt.

API und Listenmodell

Die Endpunkte liegen unter /projects/:projectId/furniture-requirements, /furniture-options, /furniture-scenarios, /furniture-summary sowie /rooms/:roomId/furniture-summary. Bedarfslisten unterstützen page, pageSize (maximal 100), search, Raum, Kategorie, Status, Priorität, Verantwortlichen, Favorit, Auswahl, Bestell-/Lieferstatus und Lieferverzug. Erlaubte Sortierungen sind Name, Raum, Kategorie, Preis, Priorität, Status, Lieferdatum, Änderungsdatum und Sortierreihenfolge.

Auswahl, Szenarien und Nebenläufigkeit

Das Auswählen eines Produkts sperrt die betroffene Alternative und deren Bedarf transaktional, prüft die Version, entfernt die bisherige Auswahl und erzeugt eine Aktivität. Damit bleibt auch bei parallelen Anforderungen höchstens eine aktive Auswahl bestehen. Bedarfe, Alternativen und Szenarien besitzen Versionsnummern; veraltete Änderungen liefern HTTP 409. Automatische Szenarien wählen günstigste, bevorzugte (Auswahl, Favorit, günstigste), teuerste oder vorhandene Alternativen und können danach manuell verändert werden.

Dokumente, Ausgaben, Status und Sicherheit

furniture_option_documents referenziert ausschließlich geschützte Projektdokumente; es existiert keine zweite Dateiablage. Ausgaben können Bedarf und Alternative referenzieren. Sämtliche Unterentitäten werden zusätzlich zur authentifizierten Projektmitgliedschaft gegen die Pfad-projectId geprüft. Leser dürfen lesen und vergleichen; Eigentümer, Administratoren und Bearbeiter verwenden die bestehende Projektaktion edit. Bestellungen speichern Besteller, Nummer und Liefertermin. Teil- und Komplettlieferung sowie Verspätung werden ausgewertet. Liefererinnerungen laufen über den vorhandenen Scheduler und die bestehende ReminderDelivery-Deduplizierung; eine Terminänderung erzeugt durch das Datum im Schlüssel eine neue, wiederholte Jobläufe dagegen keine weitere Benachrichtigung.

Migration und Development-Seed

Migration 1720000007000-AddFurniturePlanning erstellt die Möbel- und Szenariotabellen und ergänzt optionale Expense-Referenzen. Der Development-Seed bleibt produktionsgesperrt und legt 16 Bedarfe, 48 Alternativen, drei Szenarien, Favoriten, Auswahlen, Bestellungen, eine Lieferung, einen Lieferverzug, sichere Dokumentmetadaten und verknüpfte Ausgaben an. Die Etagen des Seeds sind Keller, Erdgeschoss, 1. Stock und Dachboden.