94716157cf725023883fe5b7e5e0282a58a60ceb
19
Commits
| Author | SHA1 | Message | Date | |
|---|---|---|---|---|
|
|
23794304e6 |
Build ohne Warnungen, Kalendersymbol unter Linux sichtbar
#155: Die 15 Build-Warnungen sind beseitigt, keine davon war ein echter Fehler. - CS8848 (DashboardWindow): Klammern um "as string" vor dem switch; die Auswertung war schon richtig, jetzt ist sie auch eindeutig lesbar - CS8602 (PdfExporter): Style "Normal" legt MigraDoc immer an - 13x CS8618: Felder, die nur der parameterlose XAML-Konstruktor offen laesst #50: Fluent zeichnet das Kalenderblatt im CalendarDatePicker als 0,5-px-Rahmen. Unter Linux (Skalierung 1,0) fiel er weg, uebrig blieben Tageszahl und Punkt. Eigener Style mit Kalenderblatt aus ganzen Pixeln. Auf der VM in beiden Farbschemata geprueft; der Kalender klappt weiterhin auf. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
b4d8a2a647 |
Update-Pruefung regelmaessig und ab Werk an, Installation nur auf Klick
Richards Vorgabe vom 14.09.2026 (#587): Updates nie automatisch installieren, aber regelmaessig pruefen und darauf hinweisen. Bisher pruefte der Desktop genau einmal beim Start, das WebUI nur beim Seitenaufruf, und ab Werk gar nicht (UpdateCheckEnabled=false). Eine wochenlang laufende oder frisch installierte Anwendung erfuhr nie von einem neuen Release. - UpdateCheckEnabled ab Werk true, neu UpdateCheckIntervalHours (6, 1..168) - UpdateCheckBackgroundService: erste Pruefung nach 30 s, dann im Takt; laeuft auch ohne WebUI und kopflos; Hinweis im Log einmal je neuer Fassung - Registrierung ueber AddPolyTraderUpdateCheck, nicht mehr am WebUI - Desktop-Banner haengt an UpdateStatusService.Checked; "Spaeter" blendet bis zur naechsten neueren Fassung aus - WebUI-Banner holt alle 10 Minuten den vorgehaltenen Stand Auf der Linux-VM geprueft: 0.1.9 ohne Handeinstellung erkennt 0.2.0, ein Hinweis im Log, Banner erscheint, "Spaeter" blendet aus, Beenden in 0,1 s. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
14c89aea7d |
Beenden haengt nicht mehr, Update-Agent startet erst nach Bestaetigung
Beim Updatetest auf der Linux-VM (14.09.2026) zeigte sich zweierlei: 1. Nach "Beenden" blieb der Prozess unbegrenzt stehen - Fenster offen, Port zu, Main-Thread in host.StopAsync(...).GetResult(), selbst SIGTERM ohne Wirkung. Betraf jedes Beenden der Oberflaeche, nicht nur den Update-Weg. Der Main-Thread traegt nach StartWithClassicDesktopLifetime noch Avalonias SynchronizationContext, dessen Dispatcher nicht mehr pumpt. Der Stopp laeuft jetzt per Task.Run ohne diesen Kontext, mit Obergrenze 45 s und Log der Dauer. 2. Der update-agent startete schon beim Klick auf "Installieren". Seine 40 s Wartefrist verstrichen waehrend Download und 10-Sekunden-Sperre, er brach ohne Update ab. Er startet jetzt erst nach bestaetigtem Beenden, Frist 120 s. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
86b497bdbf |
Desktop: Passwortabfrage vor Konten, Geheimnissen und WebUI-Zugang
Umsetzung von #567. Entscheidung Richard, 13.09.2026: Geheimnisse verwalten wir ausschliesslich im Desktop, und selbst dort erst nach zusaetzlicher Passwortabfrage. Bisher sah und aenderte jeder, der die Desktop-Oberflaeche offen vor sich hatte: - Polymarket-Konten mit ApiKey, ApiSecret, ApiPassphrase und PrivateKey - Master-Key, OpenRouter-Key, Watchdog-Token und Lizenzschluessel - Mullvad-Account und Polygon-RPC-URL mit Alchemy-Key, offen im Editor - das WebUI-Token, per "Anzeigen" lesbar Jetzt gesperrt, bis entsperrt: - Tab "Polymarket Accounts": Gesperrt stehen die Konten gar nicht im visuellen Baum. Das Raster bleibt leer, der Editor mit den Private Keys ebenfalls; nichts ist nur verdeckt. - Master-Key erzeugen, OpenRouter-, Watchdog- und Lizenzschluessel setzen. - Mullvad-Account und Polygon-RPC-URL: mit [SensitiveSetting] markiert und im Editor ausgeblendet. - WebUI-Zugang: Gesperrt steht das Token nicht einmal maskiert im Feld. Speichern ist mitgesperrt, weil es den Feldinhalt als Token schreibt; gesperrt und leer haette es das Token geloescht. - Frei bleiben Lizenzpruefung und Test-Heartbeat, weil sie keinen Schluessel zeigen. Kern im Core (PolyTrader.Core.Security), weil nur dort testbar: - SettingsPasswordStore: PBKDF2-HMAC-SHA256, 600 000 Iterationen, Salt, eigene Datei settings-password.json neben master.key, atomar geschrieben und nur fuer den Besitzer lesbar. Nicht in server_settings.xml, die seit #561 das WebUI mitschreibt. Ein vorhandenes Passwort wird nie ueberschrieben. - SettingsLock: - erstes Festlegen mit Wiederholung und mindestens 10 Zeichen - zwei freie Fehlversuche, danach 5 s bis 5 min Wartezeit, in der auch das richtige Passwort nicht geprueft wird - Sperre nach 5 Minuten ohne geschuetzte Aktion und beim Verlassen der Einstellungen - eine unlesbare Passwortdatei entsperrt nie und gilt auch nicht still als "kein Passwort" - Protokoll ohne eingegebene Werte Oberflaeche: PasswordDialog deklarativ in .axaml, Sperr-Leiste ueber den Tabs. Die PBKDF2-Pruefung dauert etwa eine halbe Sekunde und laeuft nicht im UI-Thread. Grenzen: - Die Sperre schuetzt gegen jemanden an einer entsperrten Desktop-Sitzung. Wer Dateizugriff hat, liest master.key selbst. Deshalb gibt es kein "Passwort vergessen": Wer settings-password.json loeschen kann, braucht keins. - Die Wartezeit nach Fehlversuchen beginnt nach einem Neustart von vorn. - "Datenbankeinstellungen": Eine Ansicht dafuer gibt es im Desktop nicht; die Verbindungszeichenfolge steht nur in appsettings.Local.json. Entsteht eine, gehoert sie hinter dieselbe Sperre. Tests: 20 fuer Passwortdatei und Sperre (Festlegen, Fehlversuche, Wartezeit, Leerlauf, unlesbare Datei, Aendern, Iterationszahl aus der Datei, Dateirechte) und 5 fuer die Markierung der Geheimnisfelder. Die Oberflaeche selbst wird auf der VM abgenommen. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
c1e13f5441 |
WebUI: Server-Einstellungen ohne Geheimnisse bearbeiten
Umsetzung von #561. Entscheidung Richard, 13.09.2026: Alles, was keine Geheimnisse beruehrt, soll ueber das WebUI gehen; Geheimnisse ausschliesslich im Desktop. Eine ausdrueckliche Freigabeliste (ServerSettingsCatalog) statt Reflection. Der Desktop zeigt per Reflection alles, was ServerSettings hat. Uebernaehme das WebUI das, stuende jedes kuenftige Feld automatisch im Netz, auch ein Geheimnis. Bearbeitbar, je Feld mit Pruefung: - Farbschema und Zeitzone: nach Neustart - VPN an/aus und VPN-Standort: sofort - Blockchain-Listener: nach Neustart - Polymarket-WSS: sofort - Watchdog an/aus, Source, Instance und Intervall: sofort "Sofort" und "nach Neustart" sind am Code belegt, nicht am Feldnamen geraten. Zeitzone und Blockchain-Listener werden nur beim Start gelesen, das Farbschema haelt der ThemeManager. Nur im Desktop, Aenderungsversuch 403 und protokolliert: - Geheimnisse: Mullvad-Account, Polygon-RPC-URL (enthaelt den Alchemy-Key), Watchdog-Token, Lizenzschluessel - Watchdog-URL: an diese Adresse geht der Watchdog-Token, wer sie aendert, bekommt ihn - Mullvad-CLI-Pfad: dieses Programm wird ausgefuehrt Von den Geheimnissen zeigt das WebUI nur, ob sie gesetzt sind. OpenRouter- und Master-Key werden dafuer nicht gelesen. Gefunden dabei: MullvadVpnService baut die Kommandozeile als eine Zeichenkette ("relay set location <Wert>"). Der VPN-Standort nimmt deshalb nur Mullvad- Kennungen an (cz, cz-prg). "cz account login 999" wird abgelehnt, ein Test haelt das fest. Source und Instance gehen als JSON ans Deploymentcenter und sind auf Kennungszeichen begrenzt. POST prueft alle Werte zuerst und schreibt dann alles oder nichts, ueber ServerSettingsFile. Danach zieht er den laufenden Stand nach: das Singleton, MullvadVpnService.ReloadSettings und WatchdogHeartbeatService.ReloadSettings. Desktop - bisher schrieb er eine WebUI-Aenderung still zurueck: Die Einstellungen wurden einmal beim Oeffnen geladen, und "Speichern", "Watchdog-Token setzen" und "Lizenzschluessel setzen" schrieben jeweils das ganze alte Objekt zurueck. Jetzt: - Speichern vergleicht innerhalb der Dateisperre den Dateistand vom Laden und verweigert, wenn sich die Datei inzwischen geaendert hat. - Token und Lizenzschluessel schreiben nur noch ihr eigenes Feld. - Eine unlesbare Datei sperrt das Speichern, statt Vorgaben zu zeigen, die beim Speichern die Schluessel geloescht haetten. Die WebUI-Ansicht zeigt je Feld den Wirkungsvermerk und schickt nur, was geaendert wurde. Der Leak-Test legt seine Kanarienwerte jetzt auch in die Einstellungsdatei, sonst liefe die neue Route gegen eine leere Datei. Nicht durch Unit-Tests abgedeckt: die Desktop-Aenderung an SettingsWindow (Oberflaechenklasse). Sie wird mit der Sichtpruefung auf der VM abgenommen. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
68d8d6f8d2 |
Module im WebUI aktivieren und deaktivieren
Umsetzung von #560. Die Ansicht "Moduleinstellungen" zeigte bisher nur an, ob ein Modul laeuft. Jetzt laesst sich dort wie im Modul-Tab des Desktops festlegen, welche Module beim naechsten Start geladen werden. POST /api/modules/{name}/enabled nimmt den gewuenschten Zustand ausdruecklich entgegen ({"enabled": true|false}) und schaltet nicht einfach um. Zwei Klicks aus zwei Fenstern heben sich damit nicht auf, und ein wiederholter Aufruf aendert nichts mehr. Fehlerfaelle: - Unbekanntes Modul: 404. - Modul mit Aktivierungs-Blocker: 409. - Fehlender Zustand: 400. Die Pruefung war zuerst lueckenhaft, der Test hat es gefunden: Mit "bool Enabled" machte ein leerer Rumpf {} daraus false, und ein unvollstaendiger Aufruf haette das Modul deaktiviert. Gemeinsame Quelle statt Kopien: - KnownModules: Die Modulliste stand viermal im Code (Program, CoreViews, ModuleViews, hartkodiert im WebUI). Der Start registriert jetzt die eine Liste. - ModuleActivationView: Die Statusregeln des Desktops ("Aktiv - stoppt nach Neustart" usw.) liegen im Core. Desktop und WebUI zeigen dasselbe. ServerSettingsFile - gefunden, bevor das WebUI in die Datei schreiben durfte: ServerSettings.Load verschluckt jeden Lesefehler und liefert Vorgaben. "Frisch lesen, ein Feld aendern, speichern" haette eine gesperrte oder beschaedigte server_settings.xml durch Vorgaben ersetzt, und mit ihr Lizenzschluessel, Watchdog-Token, Mullvad-Account und Alchemy-Key. Genau so schrieb auch der Modul-Schalter des Desktops. ServerSettingsFile: - liest streng und schreibt bei unlesbarer Datei nichts, - schreibt atomar ueber eine Nachbardatei, - erhaelt unter Linux die Dateirechte, - serialisiert Aenderungen prozessweit. Der Desktop-Schalter benutzt ihn jetzt ebenfalls. Tests: Lizenzschluessel, Token und Alchemy-Key bleiben beim Umschalten in der Datei; eine kaputte Datei bleibt Byte fuer Byte unveraendert und die Anzeige bietet dann kein Umschalten an; Blocker, 404, 400, Idempotenz; die Statustabelle; strenges Lesen, atomares Schreiben und Rechte am Dateiobjekt. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
78a2f85b94 | Standardport für WebUI von 5001 auf 6001 geändert | ||
|
|
10f928eb4e | Paralleles WebGUI mit Kestrel, Token-Sicherung und SSE-Logs implementiert | ||
|
|
28b3aedec7 |
Vier Befunde der Sichtpruefung behoben: Farbschema, Grids, Diagramme, Kontrast
#383 Farbschema "System" kehrte sein Versprechen um. ThemeManager.IsDark verglich ActualThemeVariant der Anwendung mit Dark; bei "System" steht dort Default, waehrend die Fenster selbst nach hell oder dunkel aufloesen. IsDark war damit im Auslieferungszustand immer false - Symbol, Beschriftung und Toggle() haengen alle an diesem Wert. Gelesen wird jetzt die angeforderte Variante, bei "System" die Betriebssystem-Einstellung. Derselbe Fehler steckte in Brush(): die Methode suchte bei "System" in den hellen Farben, waehrend dunkel gezeichnet wurde - betroffen war genau das, wofuer es sie gibt (Zeilenfarben, KPI-Vorzeichen). Neu ist ausserdem, dass eine Umstellung am Betriebssystem ThemeChanged ausloest, solange "System" gilt. #384 Sternspalten quetschten die Endspalten weg. Der Merksatz aus #56 galt bisher nur fuer gridTraders. Angewandt auf gridOpen und gridClosed sowie auf die uebrigen Grids, deren Spaltensumme den sichtbaren Bereich uebersteigt (gridTrades, gridJobs, gridLedger, gridCandidates, gridPositions, gridHistory). Auto statt Stern, dazu MaxWidth 360 - anders als "Name" in #56 traegt "Markt" ganze Fragesaetze und wuerde die Zahlenspalten sonst aus dem Blick schieben. Grids mit weniger Spalten als Platz behalten ihre Sternspalte. #385 Gewinntage wurden rot gezeichnet. Eine ColumnSeries hat genau ein Fill fuer alle ihre Balken; gefaerbt wurde deshalb nach der Summe ueber alle Tage. Jetzt zwei Reihen an denselben Positionen - Gewinne in der einen, Verluste in der anderen, Luecken als null. "PnL je Modul" faerbt ebenfalls nach Vorzeichen: zwei Diagramme nebeneinander mit verschiedenen Leseweisen waeren schlechter als beide ohne. #386 Drei Kleinigkeiten. Die Equity-Achse beschriftete zehn Teilstriche mit zwei Daten - unter drei Tagen kommt jetzt die Uhrzeit dazu, darueber gilt hoechstens ein Teilstrich je Tag. "Deaktivierte Module" sah aus, als fehle das Bedienelement: leere Nur-Lese-Felder zeigen jetzt "—" in einer abgesetzten Flaeche. Die Abschnittsbeschriftungen der Seitenleiste lagen bei 3,65:1 statt der geforderten 4,5:1 (im Bild sogar 1,83:1, weil 10 px mit Sperrung ausduennen) - AppCaptionTextBrush erreicht 4,61:1 hell und 6,21:1 dunkel und bleibt deutlich leiser als die Eintraege darunter. Build gruen, 486 Tests gruen. Die Sichtpruefung auf der Linux-VM steht noch aus; die drei rein visuellen Punkte sind aus dem Quelltext begruendet, nicht im Bild belegt. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
f4e017fe58 |
Spalten wieder vollstaendig; die Kalender-Vermutung war falsch
Zwei Nacharbeiten aus der Sichtpruefung auf der Linux-VM vom 28.08.2026. Master-Trader-Grid: Die Breitenumstellung von gestern hat mehr kaputtgemacht als geheilt. Von zwoelf Spalten blieben sieben brauchbar - hinter "Winrate %" stand eine Spalte mit abgeschnittenen Werten ohne Ueberschrift, dahinter vier leere Streifen. PnL, Copy-PnL, Profit-Faktor, Ø PnL/Trade und Copy-Trades waren weder lesbar noch als Spalte erkennbar. Das ist schlimmer als der urspruengliche Befund: dort fehlten Ueberschriften, hier die Werte. Ursache war die Sternbreite auf "Name". Zwoelf Spalten passen neben dem 460 px breiten Detailbereich nicht ins Fenster; statt waagerecht zu schieben, verteilt das DataGrid den Mangel und zerdrueckt die Auto-Spalten am Ende. Jetzt steht auch "Name" auf Auto: jede Spalte behaelt ihre Breite, das Grid bekommt einen waagerechten Rollbalken. Im Bild gegengeprueft. Kalendersymbol (Befund B-9): zurueckgenommen. Die gestrige Aenderung war eine Vermutung, und sie war falsch. Die vermeintlich sinnlose Zahl im Datumsfeld ist das heutige Datum - am 26.08. eine "26", am 28.08. eine "28". Avalonia zeichnet dort die heutige Tageszahl in ein Kalenderblatt, unter Linux fehlt der Blatt-Glyph. Zwei Gegenproben liessen das Bild unveraendert: die Formatvorlage per :not(#PART_Button) vom Knopf ferngehalten, und das Farbschema gewechselt. Eine Aenderung ohne Wirkung und ohne Begruendung gehoert nicht in den Code; an ihrer Stelle steht ein Kommentar, damit der Naechste nicht dieselbe Spur verfolgt. Rein kosmetisch, Bugtracker-Item #50. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
9b2294cb4c |
Testanleitung: eigenes X-Display je Projekt fuer Parallelbetrieb
Damit mehrere Agenten gleichzeitig Oberflaechen testen koennen, bekommt jedes Projekt eine feste Displaynummer (Vorgabe Richard): :99 PolyTrader, :98 Predictalytics, :97 ClawdDotNet, :96 IBKRTrader, :95 und absteigend fuer kuenftige Projekte. Zwei Prozesse auf demselben Display sehen die Fenster des jeweils anderen - Klicks landen im falschen Programm, Aufnahmen zeigen fremde Anwendungen. Beim Durcharbeiten fielen zwei weitere Kollisionspunkte auf, die zum Parallelbetrieb dazugehoeren und mit aufgenommen wurden: - Screenshot- und Logdateien in /tmp brauchen ein Projektpraefix. /tmp/v_1.png ueberschreiben sich parallel laufende Projekte gegenseitig. - "xvfb-run -a" darf NICHT mehr verwendet werden: Das -a sucht sich selbst ein freies Display und beginnt dabei bei :99 - ausgerechnet PolyTraders Nummer. Stattdessen "xvfb-run -n <nummer>". Die Warnung ist nicht theoretisch: Auf der VM lag ein verwaister X98-Socket, entstanden durch genau so einen "xvfb-run -a"-Aufruf beim smoke-ui-Test, als :99 belegt war. Er blockierte Predictalytics' reservierte Nummer, ohne dass ein Prozess lief. Entfernt, und die Anleitung erklaert jetzt, wie man verwaiste Sockets erkennt (ls /tmp/.X11-unix/ gegen pgrep -a Xvfb lesen) und aufraeumt. Weiter ergaenzt: - pkill nie ohne Displaynummer - "pkill Xvfb" erschlaegt die Sitzungen aller anderen Projekte. - DISPLAY in jedem Skript setzen, sonst landet man auf :0, dem echten Desktop. - Die Skriptvorlage hat jetzt einen Kopf mit PROJEKT/DISP/FENSTER; das ist alles, was sich je Projekt unterscheidet. Praktisch gegengetestet. - Aufraeumabschnitt und Belegungsliste um Displays und Verzeichnisse erweitert. Nebenbei aufgefallen: Das PolyTrader-Publish lag unter ~/pt-test statt ~/polytrader-test und verletzte damit die eigene Verzeichniskonvention. Umbenannt. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
dd8da3fd3f |
Arbeitsstand gesichert: Deploymentcenter-Integration (D-0 bis D-5) und Einfenster-Shell
Sicherungscommit vor dem Aufraeumen des Repos, damit nachvollziehbar bleibt, welcher Stand vor der Bereinigung galt. Build gruen, 476 Tests gruen. Zwei Straenge, die sich ueber .csproj, Program.cs und appsettings.json ueberschneiden und darum gemeinsam abgelegt werden: Deploymentcenter-Integration (P3c, Plan D-0 bis D-5 code-seitig fertig): - Deploymentcenter.Client 2.5.0 als lokales Paket, Source-Mapping erweitert - DeploymentcenterOptions, DeploymentcenterErrorReporter, LicenseGate/LicenseCli - WatchdogHeartbeatService auf die Deploymentcenter-API umgestellt (version, os, checks, metrics, status stopped) - Security: MasterKeyResolver, SecretRedactor, FilePermissions - Directory.Build.props mit zentraler Version 0.1.0 (Packager-Versionsdisziplin) - deploy/: Packager-Vorlage und systemd-Unit; echte Zugangsdaten bleiben ueber .gitignore aussen vor - setup.json fuer die Erstinstallation - UMSETZUNGSPLAN-Deploymentcenter-Integration.md; ANALYSE-Linux-Portierung.md verweist auf den neuen Plan Einfenster-Shell (UI-Redesign): - ShellWindow + ShellNavModel als Seitenleisten-Shell - WindowMenuBar und WindowMenuModel entfallen - Modul- und Kernfenster auf die Shell-Einbettung angepasst Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
7f0b05e9ba |
Avalonia-Portierung verbleibender UI-Elemente (A1 bis A4) umgesetzt
Paritaet mit dem WinForms-Referenzstand (Tag winforms-final) hergestellt: - A1 & A2 (Launcher): Account-Uebersicht DataGrid (inkl. Polymarket-Profil-Button via Launcher.LaunchUriAsync), Modul-KPI-Kacheln (7T/30T PnL & Winrate) und 3-Spalten-Live-Ueberblick (Auffaellige Trades 24h, Warnungen & Fehler heute aus den JSONL-Logs, Supervisor-KI Bericht). Periodische Aktualisierung alle 30 s eingebaut. - A3 (Copytrading): Master-Trader Werkzeugleiste um 'Neu' (AddNewTrader) und 'Loeschen' (DeleteSelectedTrader mit DialogWindow.Confirm) erweitert. - A4 (Terminal): Log-Kontextmenue fuer 'Kopieren' und 'Alles auswaehlen' an die Live-Log-Ausgabe angefuegt. Verifiziert: Solution baut fehlerfrei, 450 Tests gruen, --smoke-ui test erfolgreich. Co-Authored-By: Antigravity AI <antigravity@google.com> |
||
|
|
487ea4466d |
Dunkelmodus mit Umschalter in der Fensterleiste
Farbschema hell / dunkel / dem System folgen, umschaltbar per Klick, Stand wird in server_settings.xml gemerkt (ServerSettings.Theme). Der Editor zeigt die Einstellung automatisch als Auswahlfeld - kein Zusatzcode, weil sie ein Enum ist. - App.axaml: 18 Farb-Token je Variante (Flaechen, Rahmen, Texte, Bedeutungsfarben, Zeilenfaerbung, Trading-Umschalter, Chat-Rollen). Die Standard-Steuerelemente stellt das FluentTheme selbst um. - 22 fest verdrahtete Farben in 11 XAML-Dateien auf DynamicResource umgestellt - die wechseln damit von selbst mit. - Umschalter (Sonne/Mond) sitzt in der gemeinsamen Fensterleiste, also auf JEDEM Fenster. Der eigentliche Knackpunkt waren die Farben, die im Code gesetzt werden - die folgen dem Thema NICHT von selbst: - TradeRowPalette liefert jetzt Eigenschaften statt static readonly, loest also bei jedem Zugriff neu auf. Im Dunkeln gedaempfte Toene statt der hellen Pastelltoene, die dort blenden und den Text unlesbar machen wuerden. - ChatEntry speichert die ROLLE statt eines fertigen Brush - dadurch stimmt der Verlauf nach dem Umschalten ohne Neuaufbau der Liste. - Launcher-Umschalter, Dashboard-KPI und die Grid-Zeilenfarben zeichnen sich ueber ThemeManager.ThemeChanged neu. - Das Terminal bleibt in beiden Schemata dunkel (Konsolen sind konventionell dunkel). Nebenbei die Anzeige-Kultur gepinnt (stand ohnehin auf der Linux-Liste): auf Linux richtet sie sich sonst nach LANG/LC_ALL, das unter systemd oft nicht gesetzt ist - dann faellt .NET auf Invariant zurueck und aus '1.234,56 USDC' wird '1,234.56 USDC'. Maschinen-I/O laeuft davon unabhaengig weiter invariant. Smoke-UI prueft jetzt zusaetzlich, dass ALLE 18 Farben in BEIDEN Varianten aufloesen - ein vertippter Ressourcenschluessel wuerde sonst still grau werden. Verifiziert: Solution baut, 450 Tests gruen, --smoke-ui gruen (10 Fenster + Editor + beide Farbschemata), App startet im gespeicherten Schema, Linux-Publish laeuft. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
669676ac60 |
Modul-Fenster nach Avalonia - UI-Portierung inhaltlich abgeschlossen
Alle acht Fenster laufen jetzt unter Avalonia: Launcher, Dashboard, Settings, Terminal, Server Jobs, Copytrading, ResolutionFarming, Supervisor, Accounting (+ Shutdown- und Allzweck-Dialog). - Copytrading: vier Tabs (Master-Trader mit Account-Zuweisung, Offene Trades, Geschlossene Trades mit Filterleiste, Account-Einstellungen). Zeilenfaerbung nach PnL laeuft ueber DataGrid.LoadingRow - greift damit auch bei virtualisierten Zeilen, anders als das fruehere Faerben in DataBindingComplete. - ResolutionFarming: Kandidaten, Positionen, Historie, Settings - je Konto. - Supervisor: Analyse-Chat gegen den Agenten (Tool-Fortschritt in der Statuszeile), Dossiers mit Markdown-Ansicht, Berichte, Counterfactuals. - Accounting: KPI-Kacheln, Monats-BWA, Ledger, Abruf/Status, PDF- und CSV-Export ueber den plattformneutralen Datei-Dialog. Der SettingsEditor traegt wie erwartet die drei restlichen PropertyGrid-Stellen (Master-Trader, Account-Einstellungen, ResolutionFarming) mit je einem Aufruf. ENTSCHEIDUNG - Modul-Fenster liegen in der App, nicht in den Modulen (begruendet in Views/Modules/README.md): Die App ist der Kompositionswurzel und referenziert ohnehin alle Module. So bleiben die Modulprojekte FREI VON AVALONIA, was fuer den kopflosen Linux-Betrieb den Ausschlag gibt - der Daemon soll keine GUI-Bibliothek mitschleppen. Verifiziert: kein Modul zieht Avalonia. Registrierung in Shell/ModuleViews.cs, und zwar nur fuer tatsaechlich geladene Module - ein per DisabledModules abgeschaltetes Modul bekommt gar kein Fenster. Nebenbei: eigene View-Model-Typen CopyOpenTradeRow/CopyClosedTradeRow statt des Modul-Modells ClosedTradeRow - sie tragen den aufgeloesten Master-Trader-Namen und die Zeilenfarbe, die es dort nicht gibt (und vermeiden die Namensmehrdeutigkeit). Verifiziert: Solution baut, 450 Tests gruen, --smoke-ui gruen (alle 8 Fenster + Launcher + Dialog + Editor-Pruefung), App laeuft real mit allen Trading-Diensten, Linux-Publish laeuft. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
929fa20ee0 |
Terminal nach Avalonia + konfigurierbare Zeitzone (P2-Kern)
Alle vier Core-Fenster sind damit portiert. TERMINAL: - Live-Ausgabe als virtualisiertes ItemsControl ueber eine begrenzte Zeilenliste statt RichTextBox. Damit entfaellt das Auto-Clear der WinForms-Fassung, das bei Erreichen der Zeichengrenze den GESAMTEN Verlauf verwarf - jetzt werden nur die aeltesten Zeilen verdraengt (Ringpuffer, 5000 Zeilen), der juengste Verlauf bleibt immer sichtbar. Die Zeilenzahl steht in der Statuszeile. - Log-Viewer unveraendert im Funktionsumfang: JSONL-Tagesdateien, Filter nach Datum, Level, CID und Volltext, Doppelklick uebernimmt die CID (Signal-Kette verfolgen). ZEITZONE (Befund aus der Linux-Analyse, hier faellig geworden): Die Terminal-Ansicht rechnete hart gegen die WINDOWS-ID 'W. Europe Standard Time'. Auf Linux traegt die nur ueber die ICU-Zuordnung und faellt ganz aus, wenn ICU fehlt oder InvariantGlobalization gesetzt ist - das Fenster haette beim Oeffnen geworfen. Neu: PolyTraderSharp.Services.AppTimeZone + ServerSettings.ApplicationTimeZoneId (Default 'Europe/Berlin', IANA-Schreibweise). Aufloesung versucht die ID direkt, dann die jeweils andere Schreibweise (IANA<->Windows), zuletzt die Systemzeitzone - ein unbekannter Wert ist damit nie fatal, sondern erzeugt nur eine Warnung. Beide Programm-Einstiege setzen sie einmalig beim Start; laut Vorgabe wird sie bei der Installation festgelegt und nicht im laufenden Betrieb gewechselt (Aenderung verschiebt Logdatei-Tagesgrenzen). 8 neue Tests (AppTimeZoneTests) halten fest: IANA- UND Windows-ID liefern denselben UTC-Versatz (Winter +1, Sommer +2), unbekannte IDs fallen mit Warnung auf die Systemzeitzone zurueck, leere Angabe = Systemzeitzone, UTC wird korrekt umgerechnet. Verifiziert: Solution baut, 450 Tests gruen, --smoke-ui gruen (6 Fenster + Editor-Pruefung, Zeitzone loest als Europe/Berlin auf), App laeuft real, Linux-Publish laeuft. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
4ba8149e64 |
Settings nach Avalonia - PropertyGrid durch kategorisierten Editor ersetzt
Der PropertyGrid-Ersatz ist EIN wiederverwendbares Steuerelement statt Handarbeit je Feld: Controls/SettingsEditor zeigt ein beliebiges Einstellungsobjekt nach Richards Vorlage - Kategorie-Ueberschrift, Beschriftung links, Feld rechts, Erklaerung klein darunter. - SettingsModelBuilder liest die Attribute, die fuers PropertyGrid ohnehin gepflegt waren: [Category] gruppiert, [DisplayName] beschriftet, [Description] wird zum Hinweistext, [Browsable(false)] blendet aus (Watchdog-Token, Lizenzschluessel bleiben unsichtbar). Ergebnis fuer ServerSettings: 6 Abschnitte, 15 Felder - ohne eine Zeile Feld-Code. - Layout-Regel gewahrt: WELCHE Felder es gibt, kommt als Daten; WIE ein Feld aussieht, steht deklarativ als DataTemplate je Feldtyp (Text/Zahl/Ja-Nein/Auswahl/Nur-Lese). - Damit sind auch die drei restlichen PropertyGrid-Stellen (Account-Einstellungen, Master-Trader, ResolutionFarming) mit je einem Aufruf erledigt. SettingsWindow: Server-Settings + Polymarket-Accounts, Master-Key erzeugen, OpenRouter-Key/Watchdog-Token setzen, Test-Heartbeat. Rueckmeldungen laufen ueber die Statuszeile statt ueber Dialoge - nur echte Entscheidungen bekommen einen Dialog (neu: Views/DialogWindow fuer Hinweis/Rueckfrage/maskierte Eingabe, Avalonia hat keine MessageBox). Nebenbei einen offenen Punkt der Linux-Analyse erledigt: Schluesseldateien (master.key, openrouter.key) werden jetzt per File.SetUnixFileMode auf 600 gesetzt. Auf Linux legt File.WriteAllText sonst mit ueblicher umask 644 an - weltweit lesbar. Lizenzdialog bewusst NICHT portiert: haengt am alten LicenseLabrador-SDK, das mit der Deploymentcenter-Anbindung (P3c) ohnehin ersetzt wird - waere Wegwerfarbeit. Smoke-UI prueft jetzt zusaetzlich die Feldzahl des Editors: ein Fenster kann fehlerfrei konstruieren und trotzdem leer sein, wenn die Attribute verlorengehen. Verifiziert: Solution baut, 442 Tests gruen, --smoke-ui gruen (5 Fenster + Editor-Pruefung), Linux-Publish laeuft. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
0b8728b25f |
Dashboard nach Avalonia portiert - LiveCharts2 laeuft
Drittes Fenster: KPI-Kacheln, drei Diagramme, Tradehistorie mit Suche/Filter und Modul-Aktivierung. Aufbau nach docs/UI-SPEZIFIKATION-WinForms.md. - Diagramme sind jetzt echte Steuerelemente (LiveCharts2) statt nach Bitmap gerenderter ScottPlot-Bilder: interaktiv (Tooltips/Zoom) und ohne System.Drawing. Die Auswertung kommt unveraendert aus TradeAnalytics - der Chart-Wechsel beruehrte keine Fachlogik. Das war der Zweck der bestehenden Trennung und hat sich hier ausgezahlt. - ModuleActivationInfo vom UI-Typ in den Core verschoben (PolyTrader.Core.Modularity): Aussage ueber die Modularitaet, keine Darstellungsfrage - beide Shells brauchen sie. - Modul-Tab listet auch NICHT geladene Module, sonst liessen sie sich nie reaktivieren. Blockierte Module haben eine deaktivierte Schaltflaeche statt eines Hinweisdialogs; der Grund steht ohnehin in der Spalte 'Hinweis'. WICHTIG - Avalonia 12 -> 11.3.19 zurueckgenommen: Der erste Wurf zog per Version='*' Avalonia 12.1.1. LiveCharts2 2.0.5 (die aktuellste Version) ist gegen Avalonia 11 gebaut und bricht dort zur Laufzeit: MissingFieldException 'Avalonia.Input.Gestures.PinchEvent'. Avalonia 12 ist dem Chart-Oekosystem voraus. Jetzt 11.3.19 (DataGrid folgt eigener Reihe: 11.3.13). Erst wieder anheben, wenn LiveCharts2 Avalonia 12 unterstuetzt. Verifiziert: Solution baut, 442 Tests gruen, --smoke-ui gruen (alle 4 Fenster), App laeuft real mit allen Trading-Diensten, publisht fuer linux-x64. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |
||
|
|
cd59e5c0a5 |
Avalonia-Grundgeruest: plattformneutrale App laeuft (Shell + erstes Fenster)
Neues Projekt src/PolyTrader.App.Avalonia (net10.0, Avalonia 12.1.1, LiveCharts2 2.0.5) - laeuft unter Windows und Linux aus derselben Quelle. Enthalten: - Program.cs mit bewusst getrenntem Aufbau: BuildHost() stellt Persistenz, Dienste und Module ohne jeden UI-Bezug zusammen, erst Main haengt Avalonia daran. Damit ist der kopflose Linux-Betrieb (--headless, Stufe L2) ohne Umbau erreichbar - der Schalter ist bereits drin. - AvaloniaUiHost als IModuleUiHost: gleiche Semantik wie die WinForms-Shell (ein Fenster je View, offene nach vorn holen, alles maximiert). - Fenster-Menueleiste vollstaendig DEKLARATIV (Controls/WindowMenuBar.axaml + ItemsSource auf WindowMenuModel.Entries). Loest die alte Fassung ab, die menu.Items zur Laufzeit leerte und neu befuellte - genau der Punkt, den die neue Layout-Regel verbietet. - ViewIcons fuer Avalonia: dieselben Schluessel und dieselben PNGs wie zuvor, Core und Module bleiben unveraendert. - LauncherWindow, JobsWindow, ShutdownConfirmWindow (inkl. der 10-Sekunden-Sperre). - --smoke-ui als Nachfolger der WinForms-Konstruktionspruefung; startet den Host bewusst NICHT, damit ein reiner UI-Test nicht die Trading-Engine gegen echte Endpunkte anwirft. Dabei aufgeraeumt: - JobManager.Jobs: BindingList -> ObservableCollection. BindingList implementiert kein INotifyCollectionChanged; neu registrierte Jobs waeren in Avalonia unsichtbar geblieben. - StartupHydrationService aufgeteilt in CoreStateHydrationService (Core: Accounts + Demo-Positionen) und CopyTradingHydrationService (Modul: Settings + Trader). Behebt einen latenten Fehler: bei deaktiviertem Copytrading-Modul waeren die Accounts gar nicht mehr hydriert worden, obwohl sie zum Core gehoeren. Verifiziert: Solution baut, 442 Tests gruen, --smoke-ui gruen, die App laeuft real mit Fenster und allen Trading-Diensten (Market-Sync, Master-Trader-Analyse, RF-Scanner), und publisht fuer linux-x64. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> |