Page - Backtest

abstract

Create and monitor strategy backtests — configure parameters, start a run, track progress in real-time via polling, and view performance metrics when complete.

Route

PropertyValue
Path/backtest
Filefrontend/src/app/backtest/page.tsx
Auth RequiredNo
LayoutRoot layout with sidebar
Dynamic SegmentNone

Component Tree

BacktestPage (page.tsx)
├── AppHeader (title="Backtest", subtitle="Test strategies on historical OHLCV data")
├── BacktestConfigForm
│   └── StrategySelector (populated from GET /api/v1/strategies)
│   └── Symbol + Timeframe + Date Range inputs
│   └── Initial Balance, Spread, Max LLM Calls inputs
│   └── Submit → POST /api/v1/backtest/runs
├── BacktestRunList
│   └── Run row × N (status badge, progress bar, symbol, timeframe)
│   └── Click to select → shows in BacktestResults
└── BacktestResults (shown when selectedRun !== null)
    └── Metrics cards (Win Rate, Sharpe, Max Drawdown, Profit Factor)
    └── Equity Curve chart
    └── Trade table

Data Layer

Server State — Direct fetch + polling

CallAPIEndpointTriggered When
Fetch strategiesfetch(${API_BASE_URL}/api/v1/strategies)GET /api/v1/strategiesOn mount
Fetch runsbacktestApi.listRuns({ limit: 50 })GET /api/v1/backtest/runs?limit=50On mount + every 3s while active run exists
Create runBacktestConfigForm submitPOST /api/v1/backtest/runsForm submission

Polling Logic

// Poll every 3s only when at least one run is pending/running
useEffect(() => {
  const hasActive = runs.some((r) => r.status === "pending" || r.status === "running");
  if (!hasActive) return;
  const id = setInterval(refreshRuns, 3000);
  return () => clearInterval(id); // cleanup on unmount or when no active runs
}, [runs, refreshRuns]);

Local State — useState

VariableTypeInitialPurpose
runsBacktestRunSummary[][]All recent backtest runs (last 50)
selectedRunBacktestRunSummary | nullnullCurrently viewed run in BacktestResults
strategiesStrategyItem[][]Strategy list for form selector

Page Lifecycle

Validation & Conditions

Render Conditions

ConditionWhat Shows
runs.length === 0Empty state in BacktestRunList
run.status === "pending"Gray status badge + 0% progress bar
run.status === "running"Blue progress bar (animated)
run.status === "completed"Green badge + metrics visible
run.status === "failed"Red badge + error message
selectedRun === nullBacktestResults shows placeholder
RoleLink
Backend APIAPI-POST-v1-Backtest
DB SchemaDB - backtest_runs
DB SchemaDB - strategies