wip misc; cleaup launch

This commit is contained in:
Dobromir Popov
2025-08-19 22:51:35 +03:00
parent 6ef1a63054
commit 62fa2f41ae
7 changed files with 510 additions and 195 deletions

View File

@@ -99,6 +99,8 @@ from NN.models.standardized_cnn import StandardizedCNN
# Import layout and component managers
from web.layout_manager import DashboardLayoutManager
from web.component_manager import DashboardComponentManager
from core.polymarket_client import PolymarketClient
from core.coingecko_client import CoinGeckoClient
try:
@@ -405,8 +407,116 @@ class CleanTradingDashboard:
threading.Thread(target=self._delayed_training_check, daemon=True).start()
logger.debug("Clean Trading Dashboard initialized with HIGH-FREQUENCY COB integration and signal generation")
logger.info("🌙 Overnight Training Coordinator ready - call start_overnight_training() to begin")
logger.info("Universal model toggle system initialized - supports dynamic model registration")
logger.info("Overnight Training Coordinator ready - call start_overnight_training() to begin")
logger.info("Universal model toggle system initialized - supports dynamic model registration")
# Initialize Polymarket/CoinGecko clients
try:
self.polymarket_client = PolymarketClient()
self.coingecko_client = CoinGeckoClient()
except Exception as init_ex:
logger.error("Failed to initialize external data clients: %s", init_ex)
def _build_polymarket_vs_coingecko_figure(self):
"""Build a figure comparing Polymarket scalar implied prices vs CoinGecko real prices.
- Queries Polymarket for BTC/ETH scalar markets ending in next 5 days
- Derives implied price when possible
- Fetches CoinGecko last 5 days hourly price series
- Returns a Plotly figure with two subplots (BTC and ETH)
"""
try:
# Discover markets
markets = []
if hasattr(self, 'polymarket_client') and self.polymarket_client:
markets = self.polymarket_client.discover_btc_eth_scalar_markets(days_ahead=5)
# Partition by asset
btc_markets = [m for m in markets if m.asset == 'BTC']
eth_markets = [m for m in markets if m.asset == 'ETH']
# Compute implied prices (pick most recent by end_date if multiple)
def pick_latest_implied(mkts):
implied = None
chosen = None
if not mkts:
return (None, None)
# Sort by end_date ASC and take last with valid implied
mkts_sorted = sorted(mkts, key=lambda x: (x.end_date is None, x.end_date))
for m in mkts_sorted:
ip = self.polymarket_client.derive_implied_price(m) if self.polymarket_client else None
if ip is not None:
implied = ip
chosen = m
return (implied, chosen)
btc_implied, btc_market = pick_latest_implied(btc_markets)
eth_implied, eth_market = pick_latest_implied(eth_markets)
# Fetch CoinGecko market charts
cg_btc = {}
cg_eth = {}
if hasattr(self, 'coingecko_client') and self.coingecko_client:
cg_btc = self.coingecko_client.get_market_chart('bitcoin', days=5, interval='hourly') or {}
cg_eth = self.coingecko_client.get_market_chart('ethereum', days=5, interval='hourly') or {}
# Extract prices arrays: each entry [timestamp_ms, price]
def extract_series(obj):
arr = obj.get('prices') if isinstance(obj, dict) else None
if not isinstance(arr, list):
return []
result = []
for it in arr:
if isinstance(it, list) and len(it) >= 2:
ts = it[0]
val = it[1]
try:
result.append((ts, float(val)))
except Exception:
continue
return result
btc_series = extract_series(cg_btc)
eth_series = extract_series(cg_eth)
fig = make_subplots(rows=1, cols=2, subplot_titles=("BTC", "ETH"))
# Plot CoinGecko series
if btc_series:
fig.add_trace(
go.Scatter(x=[pd.to_datetime(ts, unit='ms') for ts, _ in btc_series],
y=[v for _, v in btc_series],
name='BTC Price (CG)',
mode='lines',
line=dict(color='royalblue')), row=1, col=1)
if eth_series:
fig.add_trace(
go.Scatter(x=[pd.to_datetime(ts, unit='ms') for ts, _ in eth_series],
y=[v for _, v in eth_series],
name='ETH Price (CG)',
mode='lines',
line=dict(color='seagreen')), row=1, col=2)
# Overlay Polymarket implied point (as marker at end_date)
def add_implied_point(asset_name, implied, market, col_idx):
if implied is None or market is None:
return
dt = market.end_date
x_val = pd.to_datetime(dt) if dt else (pd.to_datetime('now'))
label = f"{asset_name} implied: {implied:.2f}"
fig.add_trace(
go.Scatter(x=[x_val], y=[implied], name=label,
mode='markers+text', text=["PM"], textposition='top center',
marker=dict(color='orange', size=8)), row=1, col=col_idx)
add_implied_point('BTC', btc_implied, btc_market, 1)
add_implied_point('ETH', eth_implied, eth_market, 2)
fig.update_layout(margin=dict(l=20, r=20, t=30, b=20), legend=dict(orientation='h'))
return fig
except Exception as ex:
logger.error("Polymarket vs CG figure error: %s", ex)
return go.Figure().add_annotation(text="Error building figure", x=0.5, y=0.5, showarrow=False)
def _on_cob_data_update(self, symbol: str, cob_data: dict):
"""Handle COB data updates from data provider"""
@@ -1303,6 +1413,21 @@ class CleanTradingDashboard:
xref="paper", yref="paper",
x=0.5, y=0.5, showarrow=False)
# NOTE: Removed duplicate callback registration for 'polymarket-eth-btc-chart'
# Polymarket vs CoinGecko panel (slow interval)
@self.app.callback(
Output('polymarket-eth-btc-chart', 'figure'),
[Input('slow-interval-component', 'n_intervals')]
)
def update_polymarket_vs_prices(n):
try:
return self._build_polymarket_vs_coingecko_figure()
except Exception as ex:
logger.error("Polymarket panel error: %s", ex)
return go.Figure().add_annotation(text="Polymarket panel error", x=0.5, y=0.5, showarrow=False)
# Display state label for pivots toggle
@self.app.callback(
Output('pivots-display', 'children'),

View File

@@ -371,6 +371,14 @@ class DashboardLayoutManager:
html.Div([
dcc.Graph(id="price-chart", style={"height": "500px"})
]),
html.Hr(className="my-2"),
html.Div([
html.H6([
html.I(className="fas fa-chart-line me-2"),
"Polymarket vs CoinGecko (BTC/ETH, next 5 days)"
], className="card-title mb-2"),
dcc.Graph(id="polymarket-eth-btc-chart", style={"height": "350px"})
])
], className="card-body p-2")
], className="card")