Strategien & Engine-Übersicht
Stand: 2026-04-16, nach Walk-Forward-Validierung auf 540 Tagen BTC/USD 1h-Daten. Diese Datei dokumentiert das aktuelle Live-System — Code und Datenresultate sind synchron, jede Konfiguration unten ist im Backtest validiert.
1. Architektur in einem Bild
┌─────────────────────────────────────────────┐
│ DATEN-PIPELINE │
│ data/downloader.py │
│ ├─ download_ohlcv() (Kraken live) │
│ ├─ download_long_history() (Binance OHLCV)│
│ └─ download_funding_rates()(Binance Perp) │
└───────────────┬─────────────────────────────┘
│ CSV
┌───────────────▼─────────────────────────────┐
│ STRATEGIEN │
│ strategies/ │
│ ├─ regime_detector.py (ADX/ATR/EMA) │
│ ├─ multi_timeframe.py (4h-Confluence) │
│ ├─ macd_strategy.py (Sub-Logik Trend) │
│ ├─ rsi_strategy.py (Sub-Logik MR) │
│ ├─ cvd_strategy.py (eigenständig) │
│ └─ adaptive_strategy.py ★ Engine-Default │
└───────────────┬─────────────────────────────┘
│ DataFrame mit Spalten:
│ signal, side, signal_source,
│ sl_price, tp_price, …
┌───────────────▼─────────────────────────────┐
│ EXEKUTIONS-LAYER │
│ │
│ Backtest │ Live │
│ ────────── │ ────── │
│ backtesting/ │ bot/ │
│ ├─ engine.py │ ├─ run_bot_v2.py ★ │
│ ├─ real_data_ │ ├─ dynamic_risk.py │
│ │ runner.py │ ├─ funding.py │
│ └─ portfolio_ │ ├─ notify.py │
│ runner.py │ └─ monitor.py │
│ │
│ beide nutzen DIESELBE Strategy-Pipeline │
│ und DIESELBEN dynamic_risk-Profile │
└──────────────────────────────────────────────┘
Kernprinzip: Backtest und Live laufen über denselben Code-Pfad. Was der Backtest sieht, sieht der Live-Bot 1:1 — nur mit echten Order-Fills statt modellierter SL/TP-Hits.
2. Strategien-Katalog
2.1 adaptive_strategy.py ★ — Default-Engine
Pipeline pro Bar:
- Regime-Erkennung (
regime_detector.detect_regime):
- ADX(14) > 20 + EMA-Slope > 0 + DI+ > DI- → TRENDING_UP - ADX(14) > 20 + EMA-Slope < 0 + DI- > DI+ → TRENDING_DOWN - ADX(14) < 17 → RANGING - ATR > 90. Perzentil → HIGH_VOLATILITY (Override) - Hysterese ±2 ADX-Punkte gegen Regime-Flipping
- Higher-Timeframe-Trend (
multi_timeframe.compute_higher_tf_trend):
- 4h-EMA-Crossover (12/26) + 1-Bar-Shift (kein Lookahead) - Liefert htf_trend ∈ {-1, 0, +1} und htf_momentum
- Indikator-Berechnung: MACD(12/26/9), RSI(14), ATR(14),
Volume-MA(20), MACD-Strength = |hist|/ATR
- Funding-Rate (optional, wenn Spalte vorhanden):
Veto bei Funding > 0.010%/8h (Long-Crowding-Schutz)
- HTF-Persistenz für Shorts: rolling-MAX
htf_trendüber 24 Bars < 0
→ nur dann Short erlaubt (filtert Pullback-Shorts in Bull-Trends)
- Entry-Auswahl pro Regime:
`` TRENDING_UP + MACD↑-Cross + HTF>0 → LONG (source: macd_trend) TRENDING_DOWN + MACD↓-Cross + HTF persistent<0 → SHORT (off by default) RANGING + RSI<28 (cross from above) + HTF>0 → LONG (rsi_reversion) SQUEEZE-Release (off by default) → LONG (squeeze_breakout) ``
- Pro-Trade-SL/TP: Strategy schreibt
sl_price/tp_priceATR-basiert
in den Output, gespiegelt von bot/dynamic_risk.RISK_PROFILES. → Backtest-Engine liest sie pro Trade → echte Konsistenz Live↔Backtest.
- Exit-Logik (
exit_mode='sl_tp_only'Default):
- SL-Hit → Engine schließt - TP-Hit → Engine schließt - HTF-Reversal (richtungsgespiegelt) → strukturelle Notbremse - Regime-Shift in HIGH_VOLATILITY → Notbremse - RSI > 55 (nur für rsi_reversion) → Mean-Reversion-Ziel erreicht - kein MACD-Cross-Down-Exit mehr (war Whipsaw-Quelle)
2.2 macd_strategy.py — Standalone (Backtest-Vergleich)
Klassischer MACD(8/21/5)-Crossover mit ATR-SL. Wird nur noch im real_data_runner als Baseline gegen die Adaptive verglichen.
2.3 rsi_strategy.py — Standalone (Backtest-Vergleich)
RSI(14)-Mean-Reversion mit VWAP-Exit (täglicher Reset!) und ATR-SL. Liefert die Sub-Logik für die rsi_reversion-Source in der Adaptive.
2.4 cvd_strategy.py — Standalone (experimentell)
Cumulative Volume Delta — schätzt Buy/Sell-Volume aus OHLCV (echte Tick-Daten wären besser, sind aber kostenpflichtig). Detektiert Preis-CVD- Divergenzen. Aktuell nicht in der Adaptive integriert.
2.5 regime_detector.py — Sub-Komponente
Nicht standalone tradeable. Liefert:
detect_regime(df)→ klassifiziert jede Barcompute_atr(df)→ ATR-Berechnungcompute_bollinger_squeeze(df)→ BB-in-KC-Squeeze + Release-Bar
2.6 multi_timeframe.py — Sub-Komponente
resample_ohlcv(df, '4h')→ höherer Timeframecompute_higher_tf_trend(df)→ mergt HTF-EMA-Trend zurück auf Basis-TF
mit 1-Bar-Shift (verhindert Lookahead)
3. Adaptive-Strategy — Default-Konfiguration
| Parameter | Default | Begründung |
|---|---|---|
macd_fast/slow/signal | 12/26/9 | Klassisch — 8/21/5 vs 12/26/9 fast identisch auf 540d, 12/26/9 etwas robuster |
adx_trend_threshold | 22 | Niedriger = mehr Trends erfasst |
adx_range_threshold | 18 | Hysterese ±2 |
rsi_oversold/exit | 30/55 | Mean-Reversion-Logik |
higher_tf | 4h | 4× LTF — bewährter Standard |
htf_ema_fast/slow | 12/26 | wie MACD-Setup |
require_htf_confirmation | True | Nur Long bei HTF>0, nur Short bei HTF persistent<0 |
trade_high_volatility | False | HIGH_VOL = Kapitalerhalt |
enable_squeeze_breakout | False | NEGATIV-Befund: 60% SL-Hit-Rate OOS |
exit_mode | 'sl_tp_only' | HEBEL #1: kein MACD-Reverse-Whipsaw |
min_volume_ratio | 0.0 | Filter getestet → Overfitting, bleibt no-op |
min/max_macd_strength | 0.0/999.0 | dito |
enable_funding_filter | True | HEBEL #3: Long-Crowding-Veto |
max_funding_for_long | 0.00010 | 0.010%/8h — datengetrieben (Q4-high WR 33%) |
min_funding_for_short | -0.00010 | spiegelbildlich |
enable_shorts | False | Spot-only Default; Backtest neutral, braucht Margin |
short_htf_persistence_bars | 24 | Falls Shorts an: HTF muss 24 Bars bearish sein |
atr_period | 14 | Standard |
4. Risk-Management — bot/dynamic_risk.py
ATR-basierte SL/TP pro Signal-Quelle. Identisch zwischen Live und Backtest (Adaptive Strategy ruft _atr_levels() auf, die RISK_PROFILES spiegelt).
RISK_PROFILES
| Profil | SL-Mult | TP-Mult | SL-Range | TP-Range | Trailing |
|---|---|---|---|---|---|
macd_trend | 2.0×ATR | 5.0×ATR | 2–5% | 4–12% | aktiv ab +3%, 1.5% Distanz |
rsi_reversion | 1.5×ATR | 2.0×ATR | 1.5–3% | 2–4% | — |
squeeze_breakout | 1.5×ATR | 4.0×ATR | 1.5–3.5% | 3–10% | aktiv ab +2.5% |
macd_trend_short | 2.0×ATR | 3.0×ATR | 2–5% | 2.5–7% | aktiv ab +2% |
default | 2.0×ATR | 3.0×ATR | 2–4% | 2.5–8% | — |
Position-Sizing
risk_amount = capital * (risk_per_trade_pct / 100) # default 1%
position_size = risk_amount / (sl_pct / 100)
position_size = min(position_size, capital * 0.15) # Cap 15%
Idee: bei kleinem SL → größere Position (gleiches Risiko); bei großem SL → kleinere Position. Cap verhindert Over-Leverage in extrem ruhigen Phasen.
5. Backtest-Engine — backtesting/engine.py
Was sie kann
- Pro-Trade-SL/TP aus Strategy-Output (
sl_price,tp_priceSpalten) ODER
Fallback auf statische BacktestConfig-Werte
- Long und Short mit korrekt gespiegelter SL/TP-Hit-Logik (high vs low)
- Maker/Taker-Fees (0.16% / 0.26% — Kraken-Default)
- Metriken: Win-Rate, PnL, Profit-Factor, Max-Drawdown, Sharpe (annualisiert)
- Equity-Curve für Drawdown-Berechnung
Runner
| Datei | Zweck |
|---|---|
backtesting/real_data_runner.py | Vergleich aller Strategie-Stufen auf BTC/USD |
backtesting/portfolio_runner.py | Multi-Asset (BTC+ETH+SOL) mit shared Capital + Korrelations-Matrix |
backtesting/timeframe_runner.py | Timeframe-Optimierung (5m/15m/1h/4h) |
backtesting/runner.py | Basis-Strategie-Vergleich |
backtesting/advanced_runner.py | naive vs adaptive |
6. Live-Bot — bot/run_bot_v2.py
Lifecycle
Init → Load State → Loop:
├─ check_daily_limits() # max_trades, max_loss
├─ fetch_candles(200) # ccxt → Kraken
├─ funding_feed.get() # Binance perp, gecacht 15min
├─ generate_signals(df) # Adaptive Pipeline
├─ if in_position:
│ ├─ trailing_stop check # ab +X% Peak-Tracking
│ ├─ stop_loss check # dynamic_risk SL
│ ├─ take_profit check # dynamic_risk TP
│ └─ signal == -1 → exit
├─ elif signal == 1:
│ ├─ calculate_dynamic_levels() # ATR-SL/TP
│ ├─ calculate_position_size() # Risk-basiert
│ └─ place_order('buy', size)
├─ save_state() # crash-safe (fcntl-locked)
└─ sleep_until_next_candle()
Komponenten
| Modul | Rolle |
|---|---|
bot/run_bot_v2.py | Hauptschleife, Order-Logik |
bot/dynamic_risk.py | ATR-basierte SL/TP/Sizing |
bot/funding.py | Binance-Funding-Feed mit Cache |
bot/notify.py | Telegram/Webhook-Notifications |
bot/monitor.py | Performance-Dashboard |
bot/signal_status.py | Signal-State-Persistenz für Dashboard |
Sicherheitsfeatures
- File-Locked State-Persistenz (
fcntl.flock) — keine Race Conditions - Position-Wiederherstellung nach Bot-Crash (
_load_state()) - API-Key-Pflicht außer im
--dry-run-Modus - Daily Loss/Trade-Limits
- Withdraw-Permission darf nicht gesetzt sein im Kraken-Key
7. Daten-Pipeline — data/downloader.py
| Funktion | Quelle | Verwendung |
|---|---|---|
download_ohlcv() | Kraken Public | Live-Bot — letzte ~720 Bars |
download_long_history() | Binance Public | Backtest — Mehrjahres-Historie (paginiert) |
download_funding_rates() | Binance Perp | Funding-Filter Daten |
CLI
# Lange OHLCV-Historie (Backtest)
python3 data/downloader.py --source binance --symbol BTC/USDT --days 540
# Funding-Rates
python3 data/downloader.py --source binance-funding --days 540
# Live-Recent (nur Kraken-kompatibel)
python3 data/downloader.py --source kraken --symbol BTC/USD --days 30
8. Walk-Forward-Resultate (BTC 540d, 2024-10 → 2026-04)
Stufe-für-Stufe (kumulativ)
| Stufe | Trades | Win% | PnL | PF | DD% |
|---|---|---|---|---|---|
| MACD naive 3/15/3 (PDF-Rezept) | 775 | 24.9% | -$258.98 | 0.48 | 26.11% |
| Adaptive [legacy] | 146 | 34.2% | -$31.16 | 0.59 | 3.80% |
| + Asym Exits | 66 | 48.5% | -$4.38 | 0.92 | 1.74% |
| + No Squeeze | 48 | 54.2% | +$0.18 | 1.00 | 1.58% |
| + Funding-Filter ★ (Default) | 48 | 54.2% | +$3.16 | 1.09 | 1.58% |
Out-of-Sample-Performance (2. Hälfte = 9 Monate)
| Metrik | Wert |
|---|---|
| Trades | 22 |
| Win-Rate | 63.6% |
| PnL | +0.95% |
| Profit-Factor | 1.74 |
| Max Drawdown | 0.39% |
| Sharpe | 1.10 |
Was getestet, aber NICHT übernommen wurde
| Hebel | Befund | Status |
|---|---|---|
| Volume-Confirmation-Filter | Overfitting (IN besser, OUT schlechter) | Code da, Default no-op |
| MACD-Strength-Filter (Goldilocks) | Overfitting auf 32 Trades | Code da, Default no-op |
| Squeeze-Breakouts | OOS 60% SL-Hit, -7.4% net | off by default |
| Long+Short (24h-Persistence) | Mehr Trades, gleiche absolute PnL, halber Sharpe | off (Spot-only) |
| Multi-Asset (ETH/SOL) | Strategie ist BTC-spezifisch — SOL 30% WR | nicht aktiv |
9. Lektionen — was die Daten gelehrt haben
- 30 Tage Backtest-Daten sind statistisch wertlos. Die alte README-
Tabelle (PF 2.85) war reines Sample-Glück. Min. 1 Jahr für glaubwürdige Aussagen, besser 18 Monate (≥ 100 Trades).
- Walk-Forward statt Single-Sample. In-Sample-Quantil-Effekte (z.B.
"hohe MACD-Strength = niedrige WR") verschwanden auf OOS — klassisches Pattern-Matching auf Noise.
- Symmetrische Indikator-Logik whippsawt. MACD für Entry _und_ Exit
verlor systematisch. Asymmetrische Exits (ATR-SL/TP + struktureller HTF-Reversal) waren der größte Einzelhebel (PF 0.59 → 0.92).
- Weniger ist mehr. Squeeze-Breakouts zu deaktivieren brachte mehr als
sie zu aktivieren — das BB-Upper-Confirmation-Signal feuert nach dem Move.
- Multi-Asset ist kein Auto-Hebel. Korrelationen waren ideal (0.09–0.30),
aber wenn 2 von 3 Assets keinen Edge haben, diversifiziert man Verluste. Strategie zuerst per Asset validieren.
- Funding-Rate ist ein realer, struktureller Edge — aber selten
getriggert. Im normalen Markt no-op, in Mania-Phasen Rettungsanker.
- Backtest-PF 1.09 ist ehrlich, nicht spektakulär. Mit Live-Slippage
wahrscheinlich Nullsumme. Realistisch: Strategie ist „nicht-verlierend" qualifiziert, nicht „verdienend". Echter Test = Live mit Mini-Capital.
10. Live-Start
# 1. .env anlegen (Kraken-API-Key, KEIN Withdraw!)
cp .env.example .env && nano .env
# 2. Daten + Funding aktualisieren
python3 data/downloader.py --source binance --days 540
python3 data/downloader.py --source binance-funding --days 540
# 3. Sanity-Check Backtest
python3 backtesting/real_data_runner.py
# 4. Dry-Run einmal laufen lassen
python3 bot/run_bot_v2.py --dry-run
# 5. Live unter PM2 (Mini-Capital $50–100)
pm2 start ecosystem.config.js --only kraken-bot
pm2 logs kraken-bot
Erfolgskriterien für die ersten 4 Wochen
- PF > 1.0 → System überlebt Slippage, weiter laufen lassen
- PF 0.8–1.0 → grenzwertig, Trade-Volumen analysieren
- PF < 0.8 → Strategie tot; ein Hebel der Backtest-Edge geht real verloren
11. Was als nächstes _wirklich_ Sinn hätte
In absteigender erwarteter Wirkung:
- Live-Validierung 4 Wochen (Mini-Capital). Mehr Backtest = mehr
Overfitting. Echte Daten sind der nächste Erkenntnis-Schritt.
- Echte Tick-Daten für CVD (Kraken WebSocket-Stream) — die
OHLCV-Approximation in cvd_strategy ist eine grobe Heuristik.
- 15m-Timeframe testen — 5–10× mehr Trades, wenn der Edge skaliert.
- Open-Interest + BTC-Dominance als Zusatz-Filter (Binance + CoinGecko).
- Conviction-basiertes Position-Sizing (z.B. größere Position wenn
HTF + Funding + Volume alle stark übereinstimmen).
Was keinen weiteren Aufwand mehr verdient (in dieser Iteration):
- Mehr MACD/RSI/ADX-Param-Tuning auf BTC 540d → Overfitting-Risiko
- Mehr Crypto-Symbole → Strategie ist BTC-spezifisch, erst Per-Asset-Tuning
- Komplexere Indikator-Kombos → der Edge ist schon ausgereizt was Indikatoren
auf Public-OHLCV liefern können