"""Web smoke: routes return 200 and render the seeded fleet + a strategy detail + healthz.""" from __future__ import annotations import datetime as dt from fastapi.testclient import TestClient from fxhnt.adapters.persistence.forward_nav import ForwardNavRepo from fxhnt.adapters.web.app import create_app from fxhnt.application.forward_models import BacktestSummary from fxhnt.application.forward_models import ForwardNavRow as Row from fxhnt.application.forward_models import ForwardSummary def _client() -> TestClient: repo = ForwardNavRepo("sqlite://") repo.migrate() at = dt.datetime(2026, 6, 14, 23, 30) repo.upsert_rows([Row("unlock", "2026-06-05", 0.01, 1.01), Row("unlock", "2026-06-06", 0.0099, 1.0201)], at) repo.upsert_summary(ForwardSummary("unlock", "2026-06-06", 2, 1.0201, 0.0201, 1.2, -0.01), "WAIT", "2/20 forward days", at) repo.upsert_backtest_summary(BacktestSummary( "xsfunding", "2026-05-30", cagr=0.12, ann_vol=0.18, sharpe=0.85, max_drawdown=-0.22, passed=True, dsr=0.61, is_sharpe=0.9, oos_sharpe=0.7, pvalue=0.03), at) return TestClient(create_app(repo)) def test_healthz() -> None: assert _client().get("/healthz").status_code == 200 def test_cockpit_lists_fleet() -> None: r = _client().get("/") assert r.status_code == 200 assert "Token-unlock dilution shorts" in r.text and "WAIT" in r.text def test_cockpit_shows_record_and_forward_columns() -> None: # Redesigned compact edges table: edge · record · forward · nav (the standalone backtest reference is # folded into the "record" column; the gate status into "forward"). The internal sleeve-id "class" # column is intentionally NOT shown — it's dev info, not user info. r = _client().get("/") assert r.status_code == 200 for header in (">edge<", ">record<", ">forward<", ">nav<"): assert header in r.text, f"column header {header!r} missing" assert ">class<" not in r.text # the internal sleeve-id dev column is removed assert "badge WAIT" in r.text # a gate status badge rendered in the forward column def test_cockpit_has_responsive_markup() -> None: r = _client().get("/") assert r.status_code == 200 assert 'class="fleet"' in r.text # fleet table marked for card reflow assert 'data-label="forward"' in r.text # per-cell labels for mobile card view def test_strategy_detail_renders_backtest_verdict() -> None: # Redesigned: the old standalone "backtest verdict"