# IBKRTrader – Architektur & Implementierungsplan > **KORRIGIERT (2026-07-27):** Vorbild ist **PolytraderSharp** (`J:\Softwareprojekte\PolytraderSharp`), > die C#-Neuentwicklung – **nicht** die veraltete Python-Version. Die frühere Fassung dieses Plans > basierte auf der Python-Vorlage und war konzeptionell falsch. Ziel ist eine **1:1-Neu-Fundamentierung** > nach PolytraderSharp, im bestehenden IBKRTrader-Repo. Ziel: modulares C#-Trading-Framework für Interactive-Brokers-Aktien, strukturell wie PolytraderSharp, nur dass statt Polymarket über IBKR gehandelt wird. --- ## 1. Ziel-Architektur (nach PolytraderSharp) ``` IBKRTrader.App (WinExe, Root) – Generic Host + Shell (Launcher) + Core-Views │ Program.cs: Host.CreateDefaultBuilder, IConfiguration, Module laden, ShellUiHost, Application.Run │ Ui/: LauncherForm, ShellUiHost, Views/ (Dashboard, Terminal, Settings, Jobs) │ ├── src/IBKRTrader.Core (classlib, net10.0-windows, UseWindowsForms) │ ├── Modularity/ IModule (Name, DbPrefix, RegisterServices, RegisterUi, Start/Stop, ActivationBlocker) │ │ ModuleView, IModuleUiHost, WindowMenu ← UI-Contract liegt im Core │ ├── Configuration/ DatabaseOptions, ServerVersion-Pinning │ ├── DependencyInjection/ AddCorePersistence(...) │ ├── Persistence/Ef/ CoreDbContext + Entities + EF-Repositories (hinter Interfaces) │ ├── Trading/ Broker-Seam, Risk, Execution, Portfolio, Domänentypen │ ├── Services/ TerminalLogger, JobManager, Hosted Services (Market-Sync etc.) │ ├── Security/ SecretProtection (Master-Key, AES-256-GCM at-rest) │ └── Hosting/ StartupHydrationService (IHostedService, hydriert State zuerst) │ ├── src/IBKRTrader.Modules.CongressTrading (classlib, referenziert NUR Core) │ ├── CongressTradingModule : IModule │ ├── Persistence/Ef/ eigener DbContext (ct_) + Repos │ ├── Services/ Scraper + Jobs (IHostedService) │ └── Ui/ CongressTradingMainForm (Tabs) via RegisterUi │ └── tests/IBKRTrader.Tests (xUnit, referenziert Core + Module) ``` ### Leitprinzipien (aus PolytraderSharp übernommen) - **Multi-Projekt**: Core = eigenes Assembly; jedes Modul = eigenes Projekt, referenziert **nur** Core. Module können einander physisch nicht referenzieren. - **Generic Host**: `Host.CreateDefaultBuilder`, `IHostedService` für alle Hintergrund-Jobs, `IOptions`/`IConfiguration`. - **Config**: `appsettings.json` + `appsettings.Local.json` (gitignored, hält Connection-String/Secrets). - **Modul-Vertrag** `IModule`: `Name`, `DbPrefix`, `RegisterServices(services, config)`, `RegisterUi(host, sp)`, `StartAsync/StopAsync`, `GetActivationBlocker(config)`. - **UI = Shell + Views**: Core und Module registrieren `ModuleView`s beim `IModuleUiHost`. Der Launcher öffnet je View ein Fenster (Einzelinstanz, Re-Open fokussiert). Gemeinsames „Fenster"-Menü (`WindowMenu`) auf jedem Form. Views sind designbare Forms mit `Initialize(sp)`. - **Persistenz**: EF Core (Pomelo/MySQL), `AddDbContextFactory`, Repositories hinter Interfaces. - **Sicherheit**: Master-Key + AES-256-GCM-Verschlüsselung von Credentials at-rest; TLS-Warnung. - **Headless-Test**: `--smoke-ui` konstruiert jede View + Launcher ohne Message-Loop. - **Module an/aus** über `ServerSettings.DisabledModules`. --- ## 2. Was aus dem bisherigen Stand übernommen wird | Bestand (Phase 0–3, Python-basiert) | Schicksal | |---|---| | Testprojekt (xUnit) | bleibt, wandert nach `tests/` | | `RiskService`, `ExecutionService`, Domänentypen | Logik bleibt → Core/Trading (Feinschliff) | | CongressTrading Scraper/Repo | Inhalt bleibt → eigenes Modul-Projekt (auf EF/IHostedService umgestellt) | | `IModule`/`ModuleRegistry`/`WindowManager` | ersetzt durch PolytraderSharp-Contract (`IModule` neu, `ModuleView`, `IModuleUiHost`, `WindowMenu`) | | Manuelles `ServiceCollection` in Program.cs | ersetzt durch Generic Host | | `settings.json`/`SettingsService` | ersetzt durch `IConfiguration` + `appsettings.Local.json` | | Dapper + manuelle Migrationen | ersetzt durch EF Core | | `WorkerEngine`/`IWorker` | ersetzt durch `IHostedService` | --- ## 3. Re-Fundamentierungs-Phasen (Checkliste) ### R1 – Solution-Skelett (Multi-Projekt, reiner Strukturumbau, Verhalten unverändert) ✅ - [x] `src/IBKRTrader.Core` (classlib, UseWindowsForms) – `Core/` + UI-Contract (`Ui/ModuleFormBase`, `Ui/WindowManager`) - [x] `src/IBKRTrader.Modules.CongressTrading` (classlib, referenziert nur Core) - [x] Root-Projekt → `IBKRTrader.App` (WinExe), referenziert Core + Modul; Program/LauncherForm/UI-Shell bleiben - [x] `tests/IBKRTrader.Tests` – Referenzen auf Core + Modul; Fixture-Pfad angepasst - [x] Neue `.slnx`; ungenutztes HtmlAgilityPack entfernt; Build + **38/38 Tests grün**; App startet ### R2 – Core-Contracts + Generic Host + Shell-UI ✅ - [x] `IModule` (PolytraderSharp-Stil) + `ModuleView` + `IModuleUiHost` + `WindowMenu` in Core - [x] `Program.cs` → `Host.CreateDefaultBuilder`; `IConfiguration` (appsettings.json + appsettings.Local.json, gitignored) - [x] `ShellUiHost` + `LauncherForm` (View-Buttons + gemeinsames Fenster-Menü); Core-Views (Workers/Logs/Settings) als eigene Fenster - [x] CongressTrading auf neuen `IModule`-Vertrag; Modul-Worker als `IWorker` registriert - [x] `--smoke-ui` Headless-Test (alle Views + Launcher konstruieren) → grün - [ ] **Offen (R4/R5):** Worker von `WorkerEngine`/`IWorker` auf `IHostedService` umstellen (aktuell noch WorkerEngine) ### R3 – Persistenz auf EF Core **Festgelegt:** EF-Migrationen **extern** (wie PolytraderSharp) – Schema per `dotnet ef database update`, App legt keine Tabellen zur Laufzeit an. Server: **MariaDB 11.8.6** (via `--db-version` bestätigt) → Pin `new MariaDbServerVersion(new Version(11, 8, 6))`. Verbindung aus `appsettings.Local.json`. - [x] `--db-version`-Diagnose (Serverversion für den EF-Pin) - [x] **Slice 1:** `Configuration/DatabaseOptions` + `DatabaseServerVersion`-Pin (MariaDB 11.8.6); `AddCorePersistence` (`AddDbContextFactory`) + `CoreDbContext` + Entities (core_position, core_trade_history, core_budget, core_worker_log, core_settings) + Design-Time-Factory; **EF-Migration `InitialCore` erzeugt** - [x] **Slice 2:** `PortfolioService`, `BudgetService`, `TradeHistoryService` auf EF (`IDbContextFactory`) umgestellt; **5 EF-InMemory-Unit-Tests** (Buchführung real verifiziert). WorkerBase-Log folgt in Slice 4. - [x] **Slice 3:** Modul auf EF (`CongressTradingDbContext` ct_ + `CongressRepository`); `WorkerBase`-Log auf EF (core_worker_log); `CoreSettingsService` (core_settings); `CoreMigrations`/`CongressMigrations` (Dapper) entfernt; EF-Migration `InitialCongressTrading`; `appsettings.Local.json` (gitignored) als Connection-Quelle; Fallback für leeren Connection-String. **+4 EF-InMemory-Tests** (CongressRepository) - [x] **Slice 4:** IBKR-Marktdaten (`core_ibkr_*`) auf EF (3 Entities im `CoreDbContext`, Cross-Modul-Query via Raw-SQL); Migration `AddIbkr`; **Dapper + `DatabaseService` + `IBKRMigrations` vollständig entfernt** – Persistenz ist jetzt **komplett EF Core**. +4 EF-InMemory-Tests. **R3 abgeschlossen** ✅ – gesamte Persistenz auf EF Core (Migrationen: `InitialCore`, `AddIbkr`, `InitialCongressTrading`), extern via `dotnet ef database update` anzuwenden. - Hinweis: nur build-verifizierbar (Unit-Tests ohne DB); Schema-Anwendung extern via `dotnet ef database update` (env `IBKRTRADER_MYSQL`) ### R4 – Worker auf `IHostedService` ✅ - [x] `WorkerBase` implementiert `IHostedService`; `IWorker` auf Metadaten+Trigger reduziert - [x] Worker via `AddHostedService` registriert; Lebenszyklus über `AppHost.Start()`/`StopAsync()` - [x] `WorkerEngine` auf leichte Registry reduziert (WorkerInfos für UI + `TriggerWorkerAsync`) - [x] `LauncherForm` startet/stoppt keine Worker mehr; Build + 43/43 Tests + smoke-ui + App-Start grün - Hinweis: Trading-Kern (Risk/Execution/Portfolio/Broker) wurde bereits in Phase 3 gebaut und in R3 auf EF gehoben ### R5 – CongressTrading als vollständige Strategie ✅ - [x] `CongressTradingStrategy`: neuer Scrape-Trade → `TradeSignal` (buy/sell-Mapping) → Core-`IExecutionService` - [x] `CongressScrapeWorker` ruft die Strategie je neuem Trade auf (per try/catch isoliert) - [x] Modul-Fenster zeigt offene Positionen (`IPortfolioService.GetPositionsAsync("CT")`) - [x] **8 neue Tests** (Signal-Mapping/Ausführung, gemockter ExecutionService) → 51/51 grün - Hinweis: Handel bleibt durch Trading-Gate (`TradingEnabled=false`) + `NullBrokerClient` sicher aus, bis echter Broker + Freigabe ### R6 – Sicherheit + Config-Härtung ✅ - [x] `SecretProtection` (Master-Key aus env `IBKRTRADER_MASTER_KEY`/`master.key`, AES-256-GCM at-rest, selbstheilendes `enc:v1:`-Format) + `EncryptedStringConverter` (bereit für künftige IBKR-Credentials) - [x] `ConfigureSecretProtection` + TLS-Warnung (`SslMode`) beim Start; `master.key` gitignored - [x] Connection-String in `appsettings.Local.json` (gitignored) - [x] **5 SecretProtection-Tests** (Round-Trip, Idempotenz, Passthrough, Tamper/Key-Fehler) → 56/56 grün - [ ] **Offen (Nutzer-Aktion):** geleaktes DB-Passwort rotieren (liegt in Git-Historie via `grundregeln.md`, Commit `ebeb035`); EF-Schema per `dotnet ef database update` auf die DB anwenden ### R7 – Feinschliff ✅ - [x] Core-**Dashboard-View** (Gesamtüberblick: Trading-Modus, aggregierte Kennzahlen, geladene Module) + Icon - [x] `DashboardService` (aggregiert Positionen/Exposure/Trades via EF) + **2 InMemory-Tests** → 58/58 grün - [x] Tests durchgehend portiert; `--smoke-ui` deckt alle Views ab - [ ] **Nächster Meilenstein (blockiert bis Paper-Zugang):** echter `IbkrBrokerClient` über die **TWS API / IB Gateway** (entschieden 2026-07-29). Setup + Design: siehe [IBKR-Integration.md](IBKR-Integration.md). Ports Paper 4002 / Live 4001, region-agnostisch (US↔IE), `NullBroker` bleibt Default bis verifiziert. - [ ] IBKR-Account-Credentials mit `EncryptedStringConverter` speichern --- ## Kurskorrektur abgeschlossen (R1–R7) IBKRTrader entspricht jetzt strukturell dem PolytraderSharp-Konzept: Multi-Projekt (Core + Modul + App + Tests), Generic Host + `IHostedService`, `IConfiguration`, `IModule`/`ModuleView`/`ShellUiHost`, EF Core (extern migriert), Trading-Kern (Risk/Execution/Portfolio, `NullBroker`-Default), CongressTrading-Strategie, Security (Master-Key/AES-GCM). **Offen für später:** echte IBKR-Broker-Anbindung (Paper-Gateway), DB-Passwort-Rotation, EF-Schema anwenden. --- ## 4. Historie (bereits erledigt, teils zu ersetzen) - Phase 0–3 (Python-basiert): Testfundament, IModule/ModuleRegistry, LauncherForm+WindowManager, Trading-Kern (Risk/Execution/Portfolio, NullBroker). Logik brauchbar, Infrastruktur wird ersetzt. - Commits bis `2ad4b55` auf Gitea.