# Decision Log: DirektVermittlungDe **Status:** Approved **Date:** 2025-12-01 **Context:** [DvdArchitektur.txt], [Introduction.txt] Here is the formal **Decision Log** for the DirektVermittlungDe (DVD) project. This document captures the critical architectural choices, the options considered, and the rationale based on the provided requirements and constraints. # Decision Log: DirektVermittlungDe **Status:** Approved **Date:** 2025-12-01 **Context:** [DvdArchitektur.txt], [Introduction.txt] --- ## ADR-001: Separation of Metadata and Content Payload **Context:** [cite_start]The system requires an automated **Routing-Engine** to assign documents to the correct authority[cite: 4]. [cite_start]However, strict **End-to-End Encryption (E2E)** is required for sensitive data in transport and rest[cite: 23]. The server cannot route what it cannot read. **Decision:** We will implement a **Split-Payload Model**: 1. [cite_start]**Metadata (Plaintext):** A defined set of non-sensitive routing criteria (e.g., Authority ID, Reference/Aktenzeichen, Document Type) is sent as unencrypted JSON (over TLS)[cite: 3]. 2. [cite_start]**Payload (Encrypted):** The actual PDF document and sensitive message content are encrypted on the client side and stored as opaque blobs[cite: 23, 42]. **Rationale:** * [cite_start]**Compliance:** Satisfies NFR-5 (Privacy/Encryption) while enabling FR-2 (Auto-routing)[cite: 4, 23]. * [cite_start]**Performance:** The Routing Engine operates on lightweight JSON metadata (< 500ms target) without needing to decrypt/encrypt heavy files[cite: 20]. [Image of end to end encryption architecture] --- ## ADR-002: Stateless Authentication via OAuth2/JWT **Context:** [cite_start]The system must support **10k+ concurrent sessions** per region [cite: 20] [cite_start]and allow horizontal scaling (TC-2)[cite: 40]. Traditional server-side sessions (sticky sessions) would hinder scalability. **Decision:** Use **OAuth2 with OpenID Connect (OIDC)** and stateless **JWTs (JSON Web Tokens)** for session handling. * **Citizens:** Authenticate via BundID/eID. * [cite_start]**Officials:** Authenticate via Authority SSO (SAML/OIDC integration)[cite: 35]. **Rationale:** * [cite_start]**Scalability:** Allows the backend to be purely stateless; any instance can service any request (TC-2)[cite: 40]. * [cite_start]**Security:** Scopes (e.g., `citizen:write`, `official:read`) map directly to the least-privilege NFR-6[cite: 24]. --- ## ADR-003: Pagination Strategy for Interaction Threads **Context:** Interaction threads (FR-3) can grow long over time. [cite_start]The NFR-1 target is a response time of **< 300ms** for core operations[cite: 19]. Standard "Page/Offset" pagination degrades in performance as datasets grow (Offset Drifting) and handles real-time updates poorly. **Decision:** * **Cursor-based Pagination:** Used for `InteractionThreads` (chat history). The cursor will be the `timestamp` of the message. * [cite_start]**Offset-based Pagination:** Retained for the **Official’s Case List/Inbox** (FR-1.2), where users expect to "jump to page 2"[cite: 13]. **Rationale:** * [cite_start]**Performance:** Cursor seeking is O(1) complexity, ensuring the 300ms SLA is met regardless of thread length[cite: 19]. * [cite_start]**Usability:** Prevents "missing messages" or duplicates if new messages arrive while a user is scrolling (essential for chat)[cite: 8]. --- ## ADR-004: Asynchronous Processing for Data Exports **Context:** [cite_start]Authorities need to export data (PDFs + History) to their eAkte systems (FR-7)[cite: 11]. Generating these packages is resource-intensive and unpredictable in duration, which risks timing out a synchronous HTTP request. **Decision:** Implement the **Asynchronous Request-Reply Pattern**. 1. Client POSTs to `/exports` and receives `202 Accepted` + `Job-ID`. 2. [cite_start]Background workers (via Message Queue) process the PDF assembly[cite: 43]. 3. Client polls for completion or receives a webhook. **Rationale:** * [cite_start]**Resilience:** Prevents blocking the main API threads, protecting the availability goal of ≥ 99.5%[cite: 25]. * **User Experience:** Provides immediate feedback to the official instead of a loading spinner that might freeze. --- ## ADR-005: Resource Naming and Structure **Context:** [cite_start]The API must be intuitive ("Clean API") and extensible[cite: 17]. The domain model includes "Documents", "Threads", and "Routing". **Decision:** Adopt a **Document-Centric REST hierarchy**: * [cite_start]Root: `/documents` (The core "Envelope")[cite: 2]. * [cite_start]Sub-resource: `/documents/{id}/threads` (The communication context)[cite: 6]. * [cite_start]**Strict Nouns:** Use `/documents` instead of `/uploadDocument`[cite: 44]. **Rationale:** * [cite_start]**Alignment:** Matches the architectural definition of DVD being "belegorientiert" (document-driven), not just a generic chat app[cite: 17]. * **Extensibility:** Allows adding new sub-resources (e.g., `/documents/{id}/audit-log` or `/documents/{id}/appeals`) without breaking the root model. --- ## ADR-006: Data Retention & Deletion **Context:** [cite_start]Standard behavior requires data deletion after the case is closed (FR-6)[cite: 9]. [cite_start]However, users can opt for a "Personal Archive"[cite: 10, 15]. **Decision:** Implement a **TTL (Time-To-Live) Engine** on the database rows. * **Default:** `deletionDate` = `closedAt` + `gracePeriod`. * **Archive Option:** If `personalArchive` is active, `deletionDate` is set to `null` or an extended timestamp. **Rationale:** * [cite_start]**GDPR Compliance:** Ensures Privacy-by-Design (NFR-4) by automating the "Right to Erasure" / data economy principles[cite: 21]. * **Automation:** Reduces administrative overhead for cleanup. ## ADR-007: Python & ProcessPoolExecutor for Backend Services **Context:** The implementation team utilizes Agentic Coding (LLM-driven TDD). While Go/Java offers native concurrency, Python provides superior velocity with LLMs. However, Python's GIL risks blocking the event loop during CPU-intensive tasks (Encryption, PDF merging). **Decision:** Implement the Service Layer in **Python (FastAPI)** with a strict **Hybrid Concurrency Pattern**: 1. **I/O (DB/Network):** Native `async`/`await`. 2. **CPU (Crypto/PDF):** Must be offloaded to a `ProcessPoolExecutor`. **Rationale:** * **Velocity:** Maximizes the efficiency of AI coding assistants (Claude/GPT). * **Performance:** `ProcessPoolExecutor` bypasses the GIL, ensuring the main loop remains non-blocking for the 10k concurrent connections. * **Ecosystem:** Access to superior Python-based libraries for potential future AI features (classification/extraction). xxx