Files
crm-system/codebase-vs-requirements.md
leocrm-bot 0d4cbe24dd chore: clean main for new system architecture
- Old code archived on archive/legacy-v0 and feat/T1-auth
- Main contains only requirements and analysis docs
- UI Prototype: https://webspace.media-on.de/leocrm-prototype-x7k2p9/
- Ready for Phase 2: Architecture design
2026-06-28 23:07:21 +02:00

26 KiB

LeoCRM — Codebase vs Requirements Analysis

Datum: 2026-06-28 Prüfer: Codebase Explorer (Agent Zero) Methode: Read-only-Inspektion der bestehenden Codebase gegen bereinigte requirements.md


1. Bestehende Architektur-Übersicht

Stack

Komponente Code-Realität Requirements Status
Backend FastAPI 0.115.6 FastAPI kompatibel
Python 3.11+ (pyproject.toml) 3.12 (Annahme 10) ⚠️ Minor-Abweichung
Datenbank SQLite (WAL mode) PostgreSQL 16 KONFLIKT
ORM SQLAlchemy 2.0.36 (offen — architecture.md) kompatibel
Frontend Jinja2 Templates (server-side) React SPA (client-side) KONFLIKT
Auth Starlette SessionMiddleware (Cookie) Session-basiert (Cookie) kompatibel
Deployment Docker (single container) Coolify (Docker) ⚠️ Single-Container vs Multi-Container
Testing pytest (backend only) pytest + Vitest + Playwright ⚠️ Backend-only

Projekt-Struktur

app/
├── main.py              — FastAPI app, lifespan, middleware, router wiring
├── config.py            — Pydantic Settings (env: LEOCRM_*)
├── deps.py              — Auth dependencies (get_current_user, require_admin)
├── db/
│   ├── models.py        — 862 Zeilen, 15 SQLAlchemy-Modelle (alle Core, keine Plugins)
│   ├── session.py       — SQLite-Engine, SessionLocal, get_db dependency
│   └── init_db.py       — Table creation + demo seed (admin/admin)
├── routes/
│   ├── api_routes.py    — JSON auth endpoints (/api/auth/login, /api/auth/logout)
│   ├── html_routes.py   — HTML auth endpoints (/login, /logout — Jinja2)
│   ├── company_routes.py— JSON API /api/companies (CRUD, search, export)
│   ├── contact_routes.py— JSON API /api/contacts (CRUD, search)
│   ├── dms_routes.py    — JSON API /api/dms/* (folders, files, search, links, bulk)
│   ├── tag_routes.py    — JSON API /api/tags (CRUD, assign, bulk-assign)
│   ├── calendar_routes.py— JSON API /api/calendars, /api/entries (CRUD, shares, subtasks, attendees, links)
│   ├── notification_routes.py — JSON API /api/notifications
│   ├── import_routes.py — JSON API /api/companies/import, /api/contacts/import (CSV)
│   ├── public_routes.py — Public share links /api/public/share/{token}
│   └── health_routes.py — /api/health
├── services/
│   ├── auth_service.py       — bcrypt password hashing, authenticate_user
│   ├── company_service.py   — Company CRUD logic
│   ├── contact_service.py   — Contact CRUD logic
│   ├── dms_service.py       — DMS file/folder operations (26KB, größte Service-Datei)
│   ├── tag_service.py       — Tag CRUD + assignment
│   ├── calendar_service.py  — Calendar/entry/subtask/attendee/notification logic (21KB)
│   ├── permission_service.py— DMS permissions + share links
│   ├── import_service.py    — CSV import for companies/contacts
│   └── export_service.py    — CSV/XLSX export for companies
├── schemas/               — Pydantic schemas (auth, company, contact, dms, tag, calendar, common)
└── templates/             — Jinja2 HTML templates (login, register, dashboard, company_form, contact_form, contact_list, base)

Patterns

  • Monolith: Single FastAPI app, alle Module fest eingebaut
  • Dual-Interface: HTML routes (Jinja2) + JSON API routes parallel
  • Service-Layer: Business-Logik in services/, Routes sind dünn
  • SQLAlchemy 2.0: DeclarativeBase, Mapped types, mapped_column
  • Soft-Delete: deleted_at auf Company, Contact, Folder, File
  • N:M Junctions: CompanyContact, TagAssignment, FileEntityLink, EntryLink, CalendarShare
  • RBAC: 3 Rollen (admin, editor, viewer) — hardcoded in require_admin dependency
  • Demo-Seed: init_db() erstellt admin/admin + 2 Firmen + 3 Kontakte

2. Konflikte: Requirements vs Code-Realität

K1: Multi-Tenant (F-AUTH-07, F-CORE-02) — KRITISCH

Aspekt Requirements Code-Realität
tenant_id Auf allen Core-Tabellen Nirgendwo vorhanden
Tenant-Isolation ORM filtert automatisch Keine Filterung
User-Tenant-Zuordnung User kann zu mehreren Tenants gehören Nicht implementiert
Tenant-Switch UI Wechsel aktiver Tenant Nicht vorhanden
Plugin-Tabellen Müssen tenant_id haben N/A (keine Plugins)

Evidence:

  • models.py Zeile 42: class User(Base): docstring sagt explizit "Login account for LeoCRM (single-tenant)."
  • Keine tenant_id-Spalte auf Company, Contact, Folder, File, Tag, Calendar, CalendarEntry, Notification, Permission, ShareLink
  • deps.py: Session speichert nur user_id, kein tenant_id-Kontext
  • Keine Tenant-Modell-Klasse existiert

Impact: Fundamentale Architektur-Veränderung erforderlich. Jede Tabelle braucht tenant_id, ORM-Queries müssen tenant-gefiltert sein, User-Tenant-Mapping-Tabelle nötig.


K2: Plugin-System (F-PLUGIN-01, F-PLUGIN-02) — KRITISCH

Aspekt Requirements Code-Realität
Plugin-Architektur Core-Feature v1 Nicht existent
DMS/Kalender/Tags/Mail Als Plugins implementiert Fest im Core eingebaut
Plugin-Manifest Definiertes Format Nicht vorhanden
Lifecycle-Hooks install/activate/deactivate/uninstall Nicht vorhanden
Plugin-API-Endpunkte Plugins registrieren eigene Routes Nicht vorhanden
Plugin-DB-Migration Eigene Migrationen Nicht vorhanden
Plugin-Abhängigkeiten Deklarierbar Nicht vorhanden

Evidence:

  • grep -rn 'plugin\|Plugin\|manifest\|lifecycle\|activate\|deactivate' app/0 Treffer
  • DMS: models.py Folder/File/FileEntityLink + dms_service.py (26KB) + dms_routes.py — alles fest im Core
  • Kalender: models.py Calendar/CalendarShare/CalendarEntry/Attendee/EntryLink/SubTask + calendar_service.py (21KB) + calendar_routes.py — fest im Core
  • Tags: models.py Tag/TagAssignment + tag_service.py + tag_routes.py — fest im Core
  • Keine Plugin-Registry, kein Plugin-Loader, kein Manifest-Format

Impact: Komplette Plugin-Architektur muss neu gebaut werden. Bestehende DMS/Kalender/Tag-Module müssen in Plugins umgewandelt werden.


K3: Datenbank — SQLite vs PostgreSQL — KRITISCH

Aspekt Requirements Code-Realität
DB-Engine PostgreSQL 16 SQLite
Connection-Pooling PostgreSQL MVCC SQLite WAL, check_same_thread=False
Concurrent Writes Multi-User fähig SQLite limitiert

Evidence:

  • config.py: db_path: str = Field(default=str(Path("/data/leocrm.db"))) → SQLite-Datei
  • config.py: database_url property → f"sqlite:///{self.db_path}"
  • session.py: SQLite-spezifische PRAGMAs (PRAGMA foreign_keys = ON, PRAGMA journal_mode = WAL)
  • session.py: connect_args={"check_same_thread": False} — SQLite-only
  • pyproject.toml: Keine psycopg2/asyncpg/psycopg-Dependency

Impact: DB-Layer muss auf PostgreSQL umgestellt werden. Session-Engine, PRAGMAs, connect_args müssen angepasst werden.


K4: Frontend — Jinja2 vs React SPA — KRITISCH

Aspekt Requirements Code-Realität
Frontend React SPA (client-side) Jinja2 Templates (server-side)
i18n DE + EN, Sprachwahl persistiert Nicht implementiert
UI-Plugin-Framework Plugins registrieren UI-Komponenten Nicht vorhanden

Evidence:

  • app/templates/: 7 Jinja2-HTML-Templates (login, register, dashboard, company_form, contact_form, contact_list, base)
  • html_routes.py: Jinja2Templates, TemplateResponse
  • Keine package.json, keine .tsx/.jsx-Dateien, kein React/Vite-Setup
  • pyproject.toml: jinja2==3.1.5 als Dependency
  • Requirements Annahme 3: "SPA-Frontend: Client-side rendering mit React SPA (bestätigt durch genehmigten Prototyp leocrm-prototype-x7k2p9)"

Impact: Komplettes Frontend muss als React SPA neu gebaut werden. Jinja2-Templates und HTML-Routes werden obsolet. UI-Plugin-Framework (F-CORE-04) muss in React integriert werden.


K5: F-CORE-01 — Event Bus — FEHLT

Aspekt Requirements Code-Realität
Event Bus Core-Feature v1 Nicht implementiert
Events emit/subscribe Typisiert, Payload, asynchron Nicht vorhanden
Plugin-Listener Registrieren beim Aktivieren N/A

Evidence: grep -rn 'event.bus\|EventBus\|event_bus\|emit\|subscribe\|listener' app/0 Treffer


K6: F-CORE-05 — Service Container / DI — FEHLT

Aspekt Requirements Code-Realität
Service Container Core-Services über Container Nicht implementiert
DI für Plugins Services injiziert N/A
Mocking für Tests Mock-Services injizierbar Nur DB-Session override

Evidence: Services werden direkt importiert (from app.services import company_service), nicht über Container. FastAPI Depends() ist das einzige DI-Muster, aber nur für Request-Scoped dependencies (DB-Session, Current-User).


K7: F-CORE-06 — API-First Architecture — TEILWEISE

Aspekt Requirements Code-Realität
Alle Features über API API-First Teilweise — API routes existieren für alle Module
UI ist API-Client UI nutzt API Jinja2 rendert server-side
API versioniert z.B. /api/v1/ Keine Versionierung
OpenAPI/Swagger Auto-gen, dokumentiert ⚠️ FastAPI auto-gen existiert, aber nicht explizit konfiguriert
Plugin-API-Endpunkte Registrierbar N/A
KI-Copilot nutzt API Gleiche Endpunkte Nicht implementiert

Evidence:

  • API routes: /api/companies, /api/contacts, /api/dms/*, /api/tags/*, /api/calendars, /api/entries, /api/notifications, /api/auth/*
  • Kein /api/v1/ Prefix — alle routes sind unversioniert
  • FastAPI generiert automatisch OpenAPI unter /openapi.json, aber nicht explizit konfiguriert oder dokumentiert
  • HTML routes existieren parallel (/login, / dashboard) — UI ist NICHT API-Client

K8: F-CORE-07 — Async Job Queue — FEHLT

Aspekt Requirements Code-Realität
Queue-System Background-Jobs asynchron Nicht implementiert
Retry-Logic Automatische Retries Nicht vorhanden
Dead-Letter-Queue Bei wiederholtem Fehlschlag Nicht vorhanden
Job-Status UI Sichtbar im UI Nicht vorhanden

Evidence: grep -rn 'celery\|Celery\|queue\|Queue\|async_job\|background_job\|job_queue' app/0 Treffer


K9: F-CORE-08 — Caching-Strategie — FEHLT

Aspekt Requirements Code-Realität
Cache-Backend Sessions, Query-Cache, Plugin-Data Nicht implementiert
Cache-Invalidierung Event-basiert N/A
TTL-Caching Fallback Nur @lru_cache für Settings

Evidence: grep -rn 'cache\|Cache\|redis\|Redis' app/ → nur functools.lru_cache in config.py für Settings-Caching. Kein Redis, kein Query-Cache.


K10: F-CORE-09 — User-Profile und Preferences — FEHLT

Aspekt Requirements Code-Realität
User-Profile Profil mit Preferences Nicht implementiert
Sprache/Zeitzone/Theme Umschaltbar Nicht vorhanden
Dashboard-Konfiguration Konfigurierbar Nicht vorhanden
Plugin-Preferences Eigene Felder registrierbar N/A

Evidence: User-Modell hat nur: id, username, password_hash, role, personal_folder_id, default_calendar_id, created_at. Keine Preferences, keine Sprache, keine Zeitzone.


K11: F-CORE-10 — Storage-Backend — FEHLT

Aspekt Requirements Code-Realität
S3-kompatibel Konfigurierbar Nicht implementiert
Lokales Volume Alternative Lokales Dateisystem
Presigned-URLs Download ohne Plugin-Code Nicht vorhanden
Storage-Service Core-Service für Plugins Direkter Dateizugriff

Evidence:

  • config.py: dms_storage_path: str = Field(default="/data/dms") — lokales Verzeichnis
  • dms_service.py: Direkter Dateizugriff via open(), Path-Operationen
  • Keine S3/MinIO/boto3-Integration
  • grep -rn 's3\|S3\|boto3\|storage_backend\|presigned' app/0 Treffer

K12: F-CORE-11 — Generic Import/Export Service — TEILWEISE

Aspekt Requirements Code-Realität
CSV-Import Mit Preview, Dry-Run, Fehler-Reporting ⚠️ Nur direkter Import ohne Preview/Dry-Run
Excel-Export Feld-Auswahl, Filterung ⚠️ CSV + XLSX Export, aber begrenzte Feld-Auswahl
Plugin-Definitionen Registrierbar N/A

Evidence:

  • import_service.py: import_companies_csv(), import_contacts_csv() — direkter Import, kein Preview, kein Dry-Run
  • export_service.py: export_companies_csv(), export_companies_xlsx() — Export funktioniert, aber nicht generisch/plugin-fähig
  • Import/Export ist hardcoded für Companies/Contacts, nicht generisch

K13: F-CORE-12 — PDF/Document Generation Service — FEHLT

Aspekt Requirements Code-Realität
PDF-Generierung Aus Templates Nicht implementiert
Template-Engine Variablen, Conditionals, Tabellen Nicht vorhanden
Storage-Integration PDFs im Storage gespeichert N/A

Evidence: grep -rn 'pdf\|PDF\|weasyprint\|reportlab\|pdfkit' app/ → nur DMS-Preview (stream existing PDFs), keine Generierung


K14: F-CORE-13 — Notification Service — TEILWEISE

Aspekt Requirements Code-Realität
In-App-Notifications Bell-Icon, Badge-Zähler ⚠️ DB-Modell existiert, keine UI
E-Mail-Channel Notifications per Mail Nicht implementiert
Preferences Pro User konfigurierbar Nicht vorhanden
Tenant-Isolation Pro Tenant isoliert N/A (single-tenant)
Plugin-Notification-Typen Registrierbar N/A

Evidence:

  • models.py: Notification-Modell existiert (id, user_id, type, title, body, related_entry_id, is_read, created_at)
  • notification_routes.py: API für List/Mark-Read existiert
  • Keine E-Mail-Integration, keine Preferences, kein Badge-Zähler in UI (Jinja2-Templates haben kein Notification-UI)

K15: F-AUTH-01 — Login mit E-Mail — KONFLIKT

Aspekt Requirements Code-Realität
Login-Feld E-Mail + Passwort Username + Passwort
Session-Cookie HttpOnly, Secure, SameSite=Strict SameSite=lax, https_only conditional

Evidence:

  • auth_service.py: authenticate_user(db, username, password) — verwendet username, nicht email
  • models.py: User.username: Mapped[str] — kein email-Feld auf User
  • deps.py: Session speichert user_id, kein Tenant-Kontext
  • main.py: same_site="lax" (requirements sagen Strict), https_only=settings.is_production (requirements sagen Secure)

K16: F-AUTH-03 — User-Verwaltung durch Admin — FEHLT

Aspekt Requirements Code-Realität
Admin legt User an E-Mail, Name, Rolle, Passwort Nicht implementiert
User-Tenant-Zuordnung User wird Tenant zugeordnet N/A
Keine Self-Registration Admin-only ⚠️ Register-Template existiert

Evidence:

  • Keine User-Management-Routes (kein /api/users, kein Admin-User-CRUD)
  • app/templates/register.html existiert — Self-Registration-Template (widerspricht Non-Goal #1)
  • init_db.py: Demo-Seed erstellt nur admin/admin

K17: F-AUTH-05 — Passwort-Reset — FEHLT

Aspekt Requirements Code-Realität
Reset-Flow E-Mail mit Reset-Link Nicht implementiert
Reset-Link Gültig 24h Nicht vorhanden

Evidence: Keine Reset-Routes, keine Reset-Templates, keine Token-Generierung.


K18: F-AUTH-07 — Multi-Tenant — FEHLT (siehe K1)

Bereits in K1 abgedeckt. Keine Tenant-Modelle, keine User-Tenant-Mapping-Tabelle.


K19: DMS/Calendar/Tags als Core vs Plugin — ARCHITEKTUR-KONFLIKT

Modul Requirements Code-Realität
DMS v2-Plugin (F-FILE/F-DMS/F-LINK/F-PERM) Core: 3 Modelle + 26KB Service + eigene Routes
Kalender v2-Plugin (F-CAL-01..18) Core: 6 Modelle + 21KB Service + eigene Routes
Tags v2-Plugin (F-TAG-01..04) Core: 2 Modelle + 8KB Service + eigene Routes
Mail v2-Plugin (F-MAIL-01..19) Nicht implementiert

Evidence: Alle Module sind direkt in models.py, services/, routes/ integriert. Keine Plugin-Grenzen, keine Plugin-Schnittstellen.

Hinweis: Requirements sagen Plugin-System ist v1-Core-Feature, aber die Module selbst sind v2-Plugins. Das bedeutet: In v1 muss das Plugin-System gebaut werden, aber DMS/Kalender/Tags können als v2-Plugins nachgezogen werden. Die bestehenden Implementierungen können als Referenz dienen, müssen aber auf Plugin-Architektur umgebaut werden.


3. Kompatibel — Was bereits passt

Session-basierte Auth (F-AUTH-01/02, Annahme 12)

  • Starlette SessionMiddleware mit signed Cookie
  • session_cookie="leocrm_session", max_age konfigurierbar
  • Login setzt request.session[SESSION_USER_ID_KEY] = user.id
  • Logout cleared session
  • Kompatibel mit Requirements (Session-basiert, Cookie-basiert)

RBAC Grundgerüst (F-AUTH-04/06)

  • 3 Rollen: admin, editor, viewer
  • require_admin dependency prüft user.role == "admin"
  • get_current_user dependency für auth-geschützte Routes
  • Kompatibel mit Requirements (3 Rollen v1)

Company/Contact CRUD (F-COMP-01..06, F-CONT-01..07)

  • Company: 27 Felder (Name, Adresse, Industrie, Revenue, etc.)
  • Contact: 29 Felder (Name, Email, Phone, Title, etc.)
  • N:M Junction: CompanyContact
  • Soft-Delete: deleted_at auf beiden
  • Pagination, Search, Filter, Sort in Routes
  • Kompatibel mit Requirements

Data-Features (F-DATA-01..04)

  • Pagination: PageResponse schema
  • Search: Query-Parameter in company/contact routes
  • Sort: Sortier-Parameter
  • Soft-Delete: deleted_at + restore functionality
  • Kompatibel mit Requirements

Health-Check (F-INFRA-01)

  • /api/health endpoint, prüft DB, gibt Status + Version
  • Nicht auth-geschützt (für Coolify/LB)
  • Kompatibel mit Requirements

Import/Export Grundgerüst (F-MIG-01, F-DATA-01/02)

  • CSV-Import für Companies/Contacts
  • CSV + XLSX Export für Companies
  • Teilweise kompatibel — fehlt Preview, Dry-Run, generische Service-Architektur

DMS-Features (als Referenz für späteres Plugin)

  • Folder-Tree mit materialized path
  • File-Upload, Preview (PDF), Soft-Delete, Restore
  • Entity-Links (N:M zu Companies/Contacts)
  • Permissions (Individual/Group/Default)
  • Share-Links mit Password + Expiry
  • OnlyOffice-Edit-Session
  • Vollständig implementiert — kann als Plugin-Referenz dienen

Calendar-Features (als Referenz für späteres Plugin)

  • Calendar CRUD, Sharing, Visibility-Toggle
  • Entries: Events/Tasks/Reminders, Kanban-Status
  • Subtasks, Attendees, Entry-Links
  • Notifications für Reminders/Invites/Shares
  • Vollständig implementiert — kann als Plugin-Referenz dienen

Tag-System (als Referenz für späteres Plugin)

  • Tag CRUD (admin-only), Color, Assignment
  • Bulk-Assign, Entity-Type polymorphic
  • Vollständig implementiert — kann als Plugin-Referenz dienen

Testing-Setup (F-TEST-01)

  • pytest mit 20+ Test-Dateien
  • conftest.py mit Fixtures
  • Coverage-Messung konfiguriert
  • Teilweise kompatibel — fehlt Vitest (Frontend) und Playwright (E2E)

4. F-CORE-Feature-Matrix

F-CORE-ID Feature Status im Code Anmerkung
F-CORE-01 Event Bus Nicht implementiert Keine Event-Infrastruktur
F-CORE-02 Tenant-Isolation Nicht implementiert Kein tenant_id, single-tenant
F-CORE-03 Plugin-DB-Migration Nicht implementiert Kein Plugin-System
F-CORE-04 UI-Plugin-Framework Nicht implementiert Jinja2, keine Plugin-UI
F-CORE-05 Service Container / DI Nicht implementiert Direkte Imports, nur FastAPI Depends
F-CORE-06 API-First Architecture ⚠️ Teilweise API routes existieren, aber HTML parallel, keine Versionierung
F-CORE-07 Async Job Queue Nicht implementiert Keine Queue-Infrastruktur
F-CORE-08 Caching-Strategie Nicht implementiert Nur lru_cache für Settings
F-CORE-09 User-Profile/Preferences Nicht implementiert User hat nur username/role
F-CORE-10 Storage-Backend Nicht implementiert Lokales Dateisystem, kein S3
F-CORE-11 Generic Import/Export ⚠️ Teilweise CSV/XLSX funktioniert, nicht generisch, kein Preview/Dry-Run
F-CORE-12 PDF Generation Nicht implementiert Keine PDF-Generierung
F-CORE-13 Notification Service ⚠️ Teilweise DB-Modell + API existiert, keine UI, kein E-Mail-Channel

Bilanz: 0/13 vollständig implementiert, 3/13 teilweise, 10/13 fehlen komplett.


5. Empfehlung: Was vor Phase 2 angepasst werden muss

Priorität 1 — Fundamentale Architektur (vor allem anderen)

  1. Datenbank-Migration: SQLite → PostgreSQL

    • config.py: database_url auf PostgreSQL umstellen
    • session.py: SQLite-PRAGMAs entfernen, PostgreSQL-Engine konfigurieren
    • pyproject.toml: psycopg[binary] oder asyncpg hinzufügen
    • docker-compose.yml: PostgreSQL-Service hinzufügen
  2. Multi-Tenant-Architektur

    • Neues Tenant-Modell + UserTenant-Mapping-Tabelle
    • tenant_id-Spalte auf ALLE Core-Tabellen (Company, Contact, Folder, File, Tag, Calendar, etc.)
    • ORM-Query-Filter: automatische tenant_id-Filterung (SQLAlchemy Event oder Query-Wrapper)
    • Session-Kontext: aktiver tenant_id in Session speichern
    • Tenant-Switch-Endpoint + UI
  3. Frontend-Wechsel: Jinja2 → React SPA

    • React-Projekt-Setup (Vite + React + TypeScript)
    • API-Client-Layer (fetch/axios gegen /api/* Endpunkte)
    • Jinja2-Templates und html_routes.py werden obsolet
    • i18n-Integration (DE + EN)
    • UI-Plugin-Framework vorbereiten (F-CORE-04)

Priorität 2 — Core-Infrastructure (F-CORE)

  1. Service Container / DI (F-CORE-05)

    • Zentralen Service-Container implementieren
    • Core-Services registrieren: DB, Cache, Event Bus, Auth, Config, Logger
    • Plugin-Schnittstelle für Service-Requests definieren
  2. Event Bus (F-CORE-01)

    • Event-Publish/Subscribe-System implementieren
    • Typisierte Events mit Payload
    • Asynchrone Verarbeitung (ggf. via Job Queue)
  3. Plugin-System (F-PLUGIN-01/02)

    • Plugin-Manifest-Format definieren
    • Lifecycle-Hooks: install, activate, deactivate, uninstall
    • Plugin-Registry + Loader
    • Plugin-API-Endpunkt-Registrierung
    • Plugin-DB-Migration (F-CORE-03)
    • Plugin-Abhängigkeiten
  4. API-Versionierung (F-CORE-06)

    • /api/v1/ Prefix für alle API-Routes
    • OpenAPI/Swagger explizit konfigurieren und dokumentieren
    • HTML-Routes entfernen (UI wird React SPA = API-Client)

Priorität 3 — Weitere Core-Infrastructure

  1. Async Job Queue (F-CORE-07) — Queue-System für Background-Jobs
  2. Caching (F-CORE-08) — Redis-Anbindung, Query-Cache, Cache-Invalidierung
  3. Storage-Backend (F-CORE-10) — S3-kompatibler Storage-Service
  4. User-Profile/Preferences (F-CORE-09) — Profil-Erweiterung, Preferences
  5. Notification Service (F-CORE-13) — E-Mail-Channel, Preferences, Badge-UI
  6. PDF Generation (F-CORE-12) — Template-Engine, PDF-Generierung
  7. Generic Import/Export (F-CORE-11) — Generischer Service, Preview, Dry-Run

Priorität 4 — Auth-Ergänzungen

  1. Login auf E-Mail umstellen (F-AUTH-01) — username → email
  2. User-Verwaltung durch Admin (F-AUTH-03) — Admin-CRUD für User, Tenant-Zuordnung
  3. Passwort-Reset (F-AUTH-05) — Reset-Flow mit E-Mail
  4. Register-Template entfernen — Self-Registration ist Non-Goal
  5. Cookie-Security anpassen — SameSite=Strict, Secure immer

Was beibehalten werden kann

  • Backend-Services (company_service, contact_service, etc.) — Business-Logik ist solide
  • Pydantic-Schemas — Können für API-Validierung weiterverwendet werden
  • DB-Modelle — Felder/Beziehungen sind korrekt, müssen nur tenant_id ergänzt werden
  • Test-Suite — pytest-Tests können erweitert werden
  • DMS/Calendar/Tag-Implementierungen — Als Referenz für spätere Plugin-Entwicklung behalten

6. Zusammenfassung

Kategorie Anzahl Status
Kritische Konflikte 4 Multi-Tenant, Plugin-System, DB, Frontend
F-CORE fehlend 10/13 Event Bus, Tenant-Isolation, Plugin-Migration, UI-Plugin, Service Container, Job Queue, Caching, User-Profile, Storage, PDF
F-CORE teilweise 3/13 API-First, Import/Export, Notification
F-CORE vollständig 0/13
Auth-Konflikte 4 Login (username vs email), User-Verwaltung, Passwort-Reset, Cookie-Security
Kompatibel 7+ Session-Auth, RBAC, Company/Contact CRUD, Data-Features, Health, DMS/Calendar/Tags (als Referenz)

Fazit: Die bestehende Codebase ist eine funktionsfähige v0.1-Implementierung (Single-Tenant, SQLite, Jinja2), die den bereinigten v1-Requirements in 4 kritischen Bereichen nicht entspricht: Multi-Tenant, Plugin-System, PostgreSQL, React SPA. 10 von 13 F-CORE-Features fehlen komplett. Die bestehende Business-Logik (Services, Schemas, Modelle) ist jedoch solide und kann als Basis für den Umbau dienen. Der Aufwand für Phase 2 ist erheblich — es handelt sich um eine Architektur-Migration, nicht um inkrementelle Erweiterungen.