Toter Code: * ApiConfiguration.ConfigureApi (29 Z.) hatte keinen Aufrufer mehr. PredictalyticsHost baut die WebApplication seit Phase 2 selbst auf (Kestrel, CORS, Swagger, Static Files); ConfigureApi war der zurueckgebliebene Zwilling aus der Zeit davor. * IAnalyticsService.GetTraitsAsync samt Implementierung. Die Methode gab konstant eine leere Liste zurueck; ihr eigener Kommentar hielt fest, dass sie ungenutzt ist. Der Endpunkt /api/traders/traits liest direkt aus dem DbContext und bleibt unveraendert. Ungenutzte Paketreferenzen: * Swashbuckle.AspNetCore aus Predictalytics.Api - wurde nur von ConfigureApi gebraucht; Swagger baut Hosting auf, das die Referenz selbst haelt. * Microsoft.EntityFrameworkCore.Design aus Predictalytics.Worker - die Design-Time-Factory liegt in Infrastructure. * Serilog.Sinks.File/.Console und Serilog.Formatting.Compact aus Predictalytics.Infrastructure - dort wird kein Logger konfiguriert, nur Serilog.Core/Events/Context verwendet. Die Sinks haengen am Hosting. Altlast-Dateien: * Spike/ - Projektdatei ohne eine einzige Quelldatei, net8.0, nicht in der Solution. * query.csx - Ad-hoc-Abfrageskript von Juli mit fest eingetragenen DB-Zugangsdaten. * NewDesign.zip (388 KB) und temp_new_design/ - Rohmaterial des Design-Entwurfs vom 15.07. Das Ergebnis liegt fertig in wwwroot/landing.html und wwwroot/docs.html. Veraltete Verweise auf den entfernten WinForms-Host: * CLAUDE.md nannte fuer die Release-Version eine csproj, die es nicht mehr gibt - sie steht seit der Zentralisierung in Directory.Build.props. * docs/BETRIEB-Deploymentcenter.md: Anbindung und BuildInfo sitzen in Predictalytics.Hosting. * docs/API.md: Die Aussage "ohne Authentifizierung" galt vor Phase 4. Jetzt mit Header X-Predictalytics-Key und den heutigen Methodennamen. * Kommentare in Directory.Build.props, DevEndpoints.cs, PredictalyticsHost.cs. Build ohne neue Warnungen (die 8 bestehenden CS86xx sind unveraendert), 126 Tests gruen. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
7.8 KiB
Predictalytics REST API — Referenz
Stand: 2026-08-23 · Interne API, nur lokal betreiben. Lesende Endpunkte sind ungeschützt, steuernde verlangen seit Phase 4 den Header
X-Predictalytics-Key, sobald in den Einstellungen ein Token hinterlegt ist (sieheApiTokenFilter;GET /api/capabilitiesmeldet der WebUI den Ist-Zustand). Interaktive Doku:/swaggerauf dem laufenden Server. Endpunkte werden ausschliesslich inApiConfiguration.MapPredictalyticsReadEndpoints()bzw.MapPredictalyticsControlEndpoints()registriert — nur dort neue ergänzen.
Konventionen: JSON mit camelCase-Feldnamen · Zeiten in UTC (ISO 8601) ·
Prozente auf 0–100-Skala · Beträge in USD · WinRate ist marktbasiert
(gewonnene abgeschlossene Märkte / abgeschlossene Märkte, nicht pro Trade).
Traders
GET /api/traders
Trader-Liste, sortiert nach CombinedScore, dann TotalPnl.
| Parameter | Typ | Default | Beschreibung |
|---|---|---|---|
skip / take |
int | 0 / 50 | Paging |
platform |
string | All | Polymarket, Limitless, … |
highlyCopyable |
bool | false | nur CopytradingScore ≥ 60 |
Antwort: Array von TraderDto — id, platform, platformUserId (Wallet),
displayName, tier, strategy, combinedScore, copytradingScore (kombinierter
Estimator-Score), copytradingQualityScore (LCB-Edge), copytradingCopyabilityScore
(Alpha-Decay/Sizing), winRate, totalPnl, totalTrades, trades30d, pnL30d,
winRate30d, estimatedBankroll, isOnWatchlist, isSuspectedBot, lastPolledAt.
Geplant (FIXPLAN D2): trait-Parameter (mehrfach = UND) und traits-Feld im DTO.
GET /api/traders/{id}
TraderDetailDto — alles aus TraderDto plus: notes, manualPriorityOverride,
Zeitfenster pnL7d/winRate7d/pnL24h/winRate24h, currentBalance
(kumulierter Cashflow seit Tracking-Beginn), Teil-Scores activityScore/
qualityScore/volumeScore/timingScore, rank, createdAt,
aiStrategySummary, recentTrades (letzte 50, TradeDto),
categoryPerformances (je Kategorie: category, totalVolume, totalPnL,
totalTrades = abgeschlossene Märkte, winningTrades, winRate 0–1).
TradeDto: id, traderId, traderName, platform, dbMarketId, marketId
(ConditionId), marketQuestion, outcome, side (Buy/Sell/Redeem/Split/
Merge/…), price, size, amount, executedAt.
GET /api/traders/{id}/deep-dive
On-the-fly-Analyse über die letzten 500 Trades (lädt bei Bedarf Preis-Historie nach —
langsamster Endpoint). Felder: classifiedStrategy, isSuspectedBot,
avgHoldDurationHours, avgPositionSizeUsd, marketsTraded, hedgingFrequency,
timingAccuracy, entryQuality, exitQuality (je 0–100, 50 = neutral),
botIndicators (string[]), summary, recentTrades (100).
GET /api/traders/{id}/positions
Offene und realisierte Positionen. Je TraderPositionDto: marketId,
marketName, category, outcomeToken, sharesHeld, avgCost, realizedPnl,
unrealizedPnl, currentPrice, lastTradeExecutedAt.
GET /api/traders/{id}/profile
TraderProfileDto: Erweitertes Profil für die Master-Trader-Analyse. Enthält:
masterStatus (None, Candidate, Master), medianHoldDurationHours, p50PositionSize,
p90PositionSize, tradesPerWeek, medianMarketVolumeUsd, medianPostFillDriftPct,
netEdgeAfterFeesPct, priceBandProfileJson, windowMetrics (Array von 60-/120-Tage Metriken).
GET /api/traders/correlation?traderIdA=…&traderIdB=…
Vergleicht zwei Trader. TraderCorrelationDto: commonMarketsCount,
sameDirectionMarketsCount, intersectionRatioA, intersectionRatioB,
agreementRatio (wie oft in gemeinsamen Märkten die gleiche Richtung gehandelt wurde).
POST /api/traders?platform=Polymarket&wallet=0x…
Trader manuell anlegen (Import + Discovery-Flag). Antwort: Trader-Id.
POST /api/traders/{id}/priority?score=…
Manuellen Prioritäts-Override setzen (ohne score: löschen).
POST /api/traders/{id}/watchlist · DELETE /api/traders/{id}/watchlist
Watchlist-Zugehörigkeit setzen/entfernen. Watchlist-Trader sind von Retention/ Cleanup ausgenommen und werden bevorzugt synchronisiert/enriched.
POST /api/traders/{id}/ai-analysis?manual=true|false
LLM-Strategie-Analyse anstoßen (synchron; manual=true nutzt das teurere Modell).
Antwort: { summary }. Persistiert aiStrategySummary, strategy, isSuspectedBot.
Markets
GET /api/markets
Aktive Märkte. Parameter: skip/take, platform, category
(z. B. Sports, Politics, Crypto), query (Textsuche in Frage/ConditionId).
Je MarketDto: id, platform, question, volume, liquidity, endDate,
isResolved.
GET /api/markets/{id}
MarketDetailDto: zusätzlich platformMarketId (ConditionId), description,
category, subcategory, resolutionOutcome, imageUrl, botActivityScore/
uniqueTradersCount/averageTradeSize (⚠ derzeit immer 0 — MarketAnalytics wird
noch nicht berechnet), outcomes (name, price), recentTrades (50).
Watchlist
GET /api/watchlist
Alle Einträge: traderId, displayName, platformUserId, platform, totalPnl,
winRate, copytradingScore, label, notes, createdAt.
Jobs (asynchrone Hintergrund-Aufträge)
Jobs werden von den Workern abgearbeitet (Worker müssen laufen!). Status:
Pending → InProgress → Completed/Failed.
| Endpoint | Wirkung |
|---|---|
GET /api/jobs?skip&take |
Liste, neueste zuerst: id, jobType, status, traderId, traderName, createdAt, startedAt, completedAt, errorMessage |
POST /api/jobs/sync/{traderId} |
Trade-Historie synchronisieren (HistorySync) |
POST /api/jobs/analyze/{traderId} |
PnL-Engine + Copytrading-Estimator (TraderAnalysis) |
POST /api/jobs/deep-resync/{traderId} |
Komplette Historie paginiert neu importieren; löscht vorher COMPACT-Aggregate und alle Positionen des Traders |
POST /api/jobs/deep-resync-pruned |
DeepResync-Jobs für alle Trader mit gepruneten Positionen/COMPACT-Trades enqueuen |
POST /api/jobs/analyze-backlog?take=50 |
TraderAnalysis-Jobs für unanalysierte Trader enqueuen (nie analysiert zuerst, dann nach TotalTrades) |
Dashboard, Suche, Alerts, Sonstiges
| Endpoint | Beschreibung |
|---|---|
GET /api/dashboard |
Kennzahlen-Übersicht: totalTraders, activeTraders24h, totalTrades, volume24h, unreadAlerts, watchlistCount, topTraders (Top 5 nach PnL7d), largestTrades (24h), recentAlerts, platformBreakdown |
GET /api/search?q=… |
Sucht Trader (DisplayName und Wallet-Adresse) und Märkte; Antwort { traders, markets } |
GET /api/alerts?count&unreadOnly |
Alert-Liste |
PUT /api/alerts/{id}/read |
Alert als gelesen markieren |
GET /api/health |
{ status, timestamp } |
Dev (Diagnose)
| Endpoint | Beschreibung |
|---|---|
GET /api/dev/verify-positions/{traderId} |
Vergleicht unsere TraderPositions mit Polymarkets /positions-API; Antwort: mismatches[], match, dbPositionsCount, apiPositionsCount |
Ein früherer
POST /api/dev/repair-dbwurde entfernt (fehlerhaftes SQL, destruktiv). Reparatur läuft über die Schaltfläche Recalculate All Traders in der Avalonia-Shell.
Geplante Erweiterungen (FIXPLAN Teil D/E — für API-Konsumenten relevant)
GET /api/traits+trait-Filter auf/api/traders;traits-Liste in den Trader-DTOs (D2).- Markt-Rendite-Metriken im Detail-DTO:
medianWinReturnPct,avgWinReturnPct,medianLossReturnPct,avgLossReturnPct,profitFactor(D2c). GET /api/traders/{id}/profile— vollständiges Analyse-Profil eines Traders in einem Aufruf (Kennzahlen + Zeitfenster + Traits + Fingerprint-Verteilungen + Kopierbarkeits-Aggregate), gedacht für externe Konsumenten (Teil E).- Out-of-Sample-Fenster (A/B), Preisband-Profil, Stop-Loss-Klassifikation, Portfolio-/Korrelations-Sicht (Teil E).