trading-system-docs/notes/trading/system-docs/modul-11-analytics.md

87 lines
4.3 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

---
type: Modul
_organized: true
---
# Modul-11: Analytics
**Status: FREIGEGEBEN** · Container `Modul-11-Analytics` · Image `analytics-service:0.1.0`
## Zweck
Auswertung der Trade-Journal-Daten aus **Modul-10** (`trade_journal`) zu reproduzierbaren Performance-Kennzahlen. Deterministische Berechnung — gleiche Datenbasis → gleiche Ergebnisse. **V1 ohne KI/ML, ohne Orders, ohne automatische Strategieänderungen.**
## Architektur / Datenfluss
```
TRADE_RECORDED (market.journal / trade.recorded)
Modul-11-Analytics ── konsumiert über Queue `analytics.input`
├── liest read-only → trade_journal (Modul-10, PostgreSQL)
├── schreibt → analytics_snapshot, strategy_performance, daily_performance
└── publiziert (opt.)→ ANALYTICS_UPDATED (market.analytics / analytics.updated)
API (Docker-intern, Port 55011):
/health, /health/ready
/analytics/portfolio Gesamt-/Portfolio-Performance
/analytics/strategy je Strategie+Version
/analytics/regime je Market Regime
/analytics/period je Monat (ab optionalem from_date)
/analytics/rebuild (POST) deterministischer Rebuild aus DB
```
Primärquelle ist `TRADE_RECORDED`; zusätzlich liest Analytics direkt aus PostgreSQL (`trade_journal`), da für reproduzierbare Auswertungen ein vollständiger, deterministischer Rebuild aus der DB sinnvoller ist. `TRADE_RECORDED`-Events triggern eine Neuberechnung (Idempotenz: identisches Event → keine Doppelzählung).
## Datenquelle & Realisationslogik
- **Nur `status = 'CLOSED'` UND `realized_pnl IS NOT NULL`** fließen in realisierte Performance ein.
- **Offene Trades** (`OPEN`) werden separat ausgewiesen (`open_trade_count`) und zählen NICHT als realisierte Trades.
- Gruppierungsfelder aus `trade_journal`: `strategy`, `strategy_version`, `symbol`, `asset_class`, `direction` (LONG/SHORT), `regime`, `signal_score`.
- Zeitraum-Gruppierung nach `exit_time` (realisierter Trades), optional ab `from_date`.
- **Keine Lookahead-/Survivorship-Tricks**: nur tatsächlich geschlossene Trades, deterministische Equity-Kurve.
## Kennzahlen (V1)
- Anzahl Trades (realisiert + offen getrennt)
- Winrate / Lossrate
- durchschnittlicher Gewinn / Verlust
- durchschnittliches R (realized_r_multiple)
- Expectancy (Währung + R)
- Profit Factor (gross_profit / gross_loss)
- Netto-PnL
- Brutto-Gewinn / Brutto-Verlust
- Max Drawdown (aus Equity-Kurve der realisierten PnL)
- Durchschnittliche Haltedauer (entry_time→exit_time, Stunden)
- Bester / schlechtester Trade
## Eigene Tabellen (Migration `migrations/001_analytics.sql`)
- `analytics_snapshot` — stabiler Snapshot der Gesamt-Performance (jeder Rebuild = neue Zeile, chronologisch append).
- `strategy_performance` — Kennzahlen je Strategie+Version.
- `daily_performance` — Tageskennzahlen (Backtesting/Reporting).
Diese fassen KEINE bestehenden Tabellen an (read-only auf `trade_journal`).
## RabbitMQ
- **Queue** `analytics.input` (durable, topic `market.journal`, Routing `trade.recorded`), manuelles ACK, Reconnect mit Backoff (1→2→4→8→16s), kein Zombie.
- **Publiziert** optional `ANALYTICS_UPDATED` (topic `market.analytics`, Routing `analytics.updated`) — frische Verbindung je Publish (Bug-Fix-Pattern aus Modul-10), `conn.close()` nach jedem Publish.
## Verifikation (20.08.2026)
| Test | Ergebnis |
|---|---|
| 17 Pure Metriken (Gewinn/Verlust, Winrate, PF, Expectancy, Max DD, Gruppierung, offene≠realisierte) | **OK** |
| 8 Idempotenz (identisches Event → keine Doppelzählung) | **OK** |
| 9 Rebuild aus DB → identische Kennzahlen | **OK** |
| 10 RabbitMQ-Reconnect (Backoff 4→8→16s, erneuter Connect, 1 Consumer) | **OK** |
| E2E 03→11 (Seed realisierter Trades, Portfolio/Strategie/Regime, DB + Idempotenz) | **OK** |
- Health/Ready: `200` Port 55011 (PostgreSQL ✓, RabbitMQ ✓, Consumer ready ✓).
- Endzustand nach Freigabe: 2 echte OPEN-Trades im Journal, 0 realisierte → Snapshot zeigt 0/2.
## Betriebshinweise
- Kein öffentlicher Port (nur `expose: 55011`).
- `restart: unless-stopped`.
- Compose-Pfad VPS: `/opt/trading-modules/docker-compose.yml`.
- Forgejo-Doku: `nexo312/trading-system-docs`, Commit-ID siehe unten.
---
*Geändert von: Rain Ocampo (Hermes)*
*Datum: 20.08.2026* — Modul-11-Analytics, Status FREIGABEGEBEN.