Run a backtest
A backtest simulates how an algorithm would have traded on historical bar data, bar by bar. It's used to gauge performance before going live.
Steps
- /dashboard/backtest
- Pick a connected account. The engine borrows that account's broker connection to pull bar history — the account must be connected, but no bot has to be running.
- Algorithm, symbol, timeframe, date range, starting balance → Run backtest.
- Takes ~5-30s (depending on bar count and container load). The result panel shows net P&L, win rate, max drawdown, equity curve and a trade-by-trade table.
Symbol IDs
Every broker uses different symbol IDs. The IDs in the dropdown cover the most common major pairs and usually match demo accounts. If the result shows "0 bars", try a different symbol ID; if it keeps failing you can search for the line in the log feed .
Known limitations
- Backtesting is a plan capability — it must be enabled on your plan. If it isn't, the page shows an upgrade note and the Run button is disabled.
- P&L is converted into your account currency when the replay can work the rate out from the instrument itself — BTCUSD or EURUSD on a USD account, or USDJPY, where the symbol's own price is the rate. A pair sharing neither currency with your account (EURJPY on a USD account) needs a third symbol's history the replay can't read, and the result says so.
- The spread is charged on every round trip; commissions and slippage are not modelled.
- Only bar-close events are replayed — no intra-bar ticks. Indicators with long lookbacks may miss the first few signals.
- Pending orders are replayed, so martingale grids fill and cancel as they would live. Fills happen at the order's price — a gap straight past a rung fills it at the rung, not at the gap.
- Maximum response is 60s. Very long ranges time out; try a narrower date range.
- Indicators need history before their first honest value — a 200-period moving average needs 200 bars. Those warm-up bars are read from before your date range, not taken out of it, and the bar count badge tells you how many were used.
How do I read the result?
The equity curve sums realized + floating P&L after every bar. Max drawdown is the peak-to-trough ratio — above 15% is usually unacceptable. Don't trust a strategy unless win rate is 50%+ and profit factor is 1.2+; with a small sample size (fewer than 50 trades) the stats can just be noise.
Studying the chart
The result chart is not just a picture of the run — it is where you check whether the strategy caught the move it was aiming at or survived by accident.
- Replay plays the run back candle by candle, so trades appear in the order the strategy decided them rather than all at once. Speed runs from 0.25× to 4×; 1× is about three candles a second. Slow it down when a single entry is the question.
- Step one candle back or forward, or jump to either end. Stepping backwards is usually what you want: the interesting question is what the strategy could see just BEFORE it entered.
- The indicator button draws the strategy's own indicators over the price, computed the same way the live bot computes them, so an entry can be read against the average it crossed or the band it touched. Lines stop at the replay position — they never run ahead of the candles. A filter that reads a different timeframe cannot be drawn on these candles and is left out rather than drawn on the wrong ones.
- Fullscreen fills the screen for a closer look; press Escape to leave. With the chart focused, Space plays and pauses and the arrow keys step.
Controls on this step
What the app checks before letting you continue, and why.
- Backtest requires a plan with the feature — Backtesting is a plan feature — if your plan doesn't include it, Run is disabled with an explanation instead of silently failing or letting you queue a request that the server will reject anyway. (In commission mode backtesting is always enabled for everyone — it's priced per run instead, shown on the pricing page.)
- A backtest won't run without the broker's contract — Pip size and lot size differ by instrument — a pip is 0.0001 on EURUSD and 0.10 on BTCUSD — and every result, plus every pip-based setting like take profit and martingale distance, is measured in them. If the engine doesn't have the broker's contract for your symbol, the run is refused rather than falling back to a default, because a result computed against the wrong contract isn't approximate, it's a different strategy.
- Commission mode: each backtest run has a price — In commission mode, every backtest run — Run backtest to Run backtest — is charged from your wallet at the fixed price shown on the pricing page, checked before the engine runs it at all: an insufficient balance is refused with the amount needed and your current balance, so a run you can't pay for never starts. There is no free run threshold for backtesting the way the screener has one — every run is priced.