Backtest API & SDK
Run strategy backtests, browse the bot leaderboard, clone bots, and paper trade — all via API.
Quick Start
# Run a funding rate backtest
curl -X POST https://cymetica.com/api/v1/backtest-labs/run \
-H "Content-Type: application/json" \
-d '{"type":"funding_rate","params":{"coin":"BTC","days":30,"capital":10000,"leverage":1,"strategy":"cross_exchange"}}'
# Get bot leaderboard
curl https://cymetica.com/api/v1/backtest/leaderboard?sort=total_return&limit=10
from event_trader import EventTrader
client = EventTrader(api_key="evt_...")
# Run a backtest
result = await client.backtest.run_lab(
type="funding_rate",
params={"coin": "BTC", "days": 30, "capital": 10000}
)
# Get leaderboard
leaderboard = await client.backtest.leaderboard(sort="total_return", limit=10)
# Get bot profile
bot = await client.backtest.bot("alpha-momentum-v2")
The JS/TS SDK's npm release is in progress — these snippets show the interface it ships with. The Python SDK and the REST API are live today.
import { EventTrader } from "cymetica-eventtrader";
const client = new EventTrader({ apiKey: "evt_..." });
// Run a backtest
const result = await client.backtest.runLab({
type: "funding_rate",
params: { coin: "BTC", days: 30, capital: 10000 }
});
// Get leaderboard
const leaderboard = await client.backtest.leaderboard({ sort: "total_return", limit: 10 });
// Get bot profile
const bot = await client.backtest.bot("alpha-momentum-v2");
# Python
pip install cymetica-eventtrader
# TypeScript / Node.js — npm release in progress; Python SDK is live today
# npm install cymetica-eventtrader
Authentication
Most read endpoints are public (no auth required). Write operations use one of two methods depending on the endpoint family: Backtest Labs runs (/api/v1/backtest-labs/*) authenticate with an API key (X-API-Key header), while bot management (clone, trigger run, update settings) requires a Bearer token from a logged-in session.
# Authenticated request
curl -H "Authorization: Bearer YOUR_TOKEN" \
https://cymetica.com/api/v1/backtest/bots/my-bot/run-backtest
Get your API key from /account → API Keys.
Backtest Labs
Run parameterized strategy backtests. Supports funding rate arbitrage, momentum, and mean reversion strategies. Max 20 concurrent backtests via Redis queue.
Request Body
funding_rate, momentum, mean_reversioncross_exchange)curl -X POST https://cymetica.com/api/v1/backtest-labs/run \
-H "Content-Type: application/json" \
-d '{
"type": "funding_rate",
"params": {
"coin": "BTC",
"days": 30,
"capital": 10000,
"leverage": 1,
"strategy": "cross_exchange"
}
}'
result = await client.backtest.run_lab(
type="funding_rate",
params={"coin": "BTC", "days": 30, "capital": 10000, "leverage": 1, "strategy": "cross_exchange"}
)
const result = await client.backtest.runLab({
type: "funding_rate",
params: { coin: "BTC", days: 30, capital: 10000, leverage: 1, strategy: "cross_exchange" }
});
Multi-Leg Backtesting — Baskets, AIBs and Themes
Backtest Labs above runs a strategy against one asset. To backtest a
basket — several legs with weights — use the endpoints below.
Basket symbols (AIB-, TREND-, EVCDX-,
RALLY-, MM-) are not accepted by the single-asset endpoints.
All results describe the past and are never a predicted return.
The API behind the “Backtest this idea” widget on /events/builder. Read-only: no card is created, no ledger or on-chain write happens, no money moves. Runs the same engine as the saved-card backtest, so an idea and a published card holding the same basket return identical numbers.
Request Body
{symbol, weight} (optional coingecko_id). Weights are relative and renormalized, so 50/30/20 equals 5/3/2.7, 30, 90, 180, 365. Anything else returns 422.Response
ending_capital_usdcnumberSimulated capital at each end of the window.
n_points).dropped_symbolsarrayLegs that could not be priced and were excluded. Always check these before trusting the numbers.
curl -X POST https://cymetica.com/api/v1/event-cards/backtest-idea \
-H "Content-Type: application/json" \
-d '{
"constituents": [
{"symbol": "BTC", "weight": 50},
{"symbol": "ETH", "weight": 30},
{"symbol": "SOL", "weight": 20}
],
"period_days": 90,
"starting_capital": 10000
}'
result = await client.basket_backtest.run(
constituents=[("BTC", 50), ("ETH", 30), ("SOL", 20)],
period_days=90,
starting_capital=10_000,
)
print(result["total_return_pct"], result["sharpe_ratio"])
print(result["unresolved_symbols"], result["dropped_symbols"])
const result = await client.basketBacktest.run({
constituents: [
{ symbol: "BTC", weight: 50 },
{ symbol: "ETH", weight: 30 },
{ symbol: "SOL", weight: 20 },
],
periodDays: 90,
startingCapital: 10000,
});
console.log(result.total_return_pct, result.sharpe_ratio);
et_basket_backtest(
constituents=[
{"symbol": "BTC", "weight": 50},
{"symbol": "ETH", "weight": 30},
{"symbol": "SOL", "weight": 20}
],
period_days=90,
starting_capital=10000
)
Give it a plain-language theme and the Tuatara semantic model selects real
trading vehicles (stocks, ETFs, crypto) and weights them by relevance. The basket
gets an MM-… symbol and a /macromarket page.
Request Body
"AI infrastructure".tuatara (relevance-weighted) or equal.crypto, equity. Omit for both.curl -X POST https://cymetica.com/api/v1/macromarket/build \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $EVENTTRADER_API_KEY" \
-d '{"theme": "AI infrastructure", "num_assets": 8, "weighting": "tuatara"}'
aib = await client.macromarket.build("AI infrastructure", num_assets=8)
print(aib["symbol"]) # e.g. "MM-AIINFRA"
const aib = await client.macromarket.build({
theme: "AI infrastructure",
numAssets: 8,
});
et_aib_build(theme="AI infrastructure", num_assets=8, weighting="tuatara")
Pass aib_symbol for an existing basket, or theme to build
and persist one first. Quota-gated: an over-quota caller gets 402
before any expensive work runs. Results are simulated, not investment advice.
Request Body
MM-… symbol. Required unless theme is given.curl -X POST https://cymetica.com/api/v1/macromarket/backtest \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $EVENTTRADER_API_KEY" \
-d '{"aib_symbol": "MM-AIINFRA", "period_days": 365}'
bt = await client.macromarket.backtest(aib_symbol="MM-AIINFRA", period_days=365)
# Or skip the build entirely and backtest a theme directly:
bt = await client.macromarket.backtest(theme="uranium miners")
const bt = await client.macromarket.backtest({
aibSymbol: "MM-AIINFRA",
periodDays: 365,
});
et_aib_backtest(aib_symbol="MM-AIINFRA", period_days=365)
et_aib_backtest(theme="uranium miners")
The headline-basket research engine behind /backtest-rally. Races strategies against BTC and can launch the winner as a Rally Card. Signal/backtest only — no orders are placed. Full reference: /backtest-rally/api.
curl -X POST https://cymetica.com/api/v1/research-backtest/run \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $EVENTTRADER_API_KEY" \
-d '{"themes": ["ai tokens"], "algo_model": "aib_sentiment", "hold_days": 2}'
run = await client.research_backtest.run(
themes=["defi tokens", "ai tokens"], hold_days=2)
result = await client.research_backtest.get(run["run_id"])
await client.research_backtest.launch_rally_card(run["run_id"], basket_index=0)
const run = await client.researchBacktest.run({
themes: ["defi tokens", "ai tokens"],
params: { hold_days: 2 },
});
const result = await client.researchBacktest.get(run.run_id);
et_research_backtest_run(params={"themes": ["ai tokens"], "hold_days": 2})
et_research_backtest_launch_rally_card(run_id="<run_id>", basket_index=0)
Bot Leaderboard
Browse ranked AI trading bots with sorting and filtering. 60-second cache on leaderboard results.
Query Parameters
total_return, win_rate, sharpe, max_drawdown (default: total_return)all)all, red, bluecurl "https://cymetica.com/api/v1/backtest/leaderboard?sort=total_return&team=red&limit=10"
leaderboard = await client.backtest.leaderboard(sort="total_return", team="red", limit=10)
const lb = await client.backtest.leaderboard({ sort: "total_return", team: "red", limit: 10 });
Bot Profiles
Get bot details, equity curves, and trade history. 60-second cache on profile data.
Path Parameters
curl https://cymetica.com/api/v1/backtest/bots/alpha-momentum-v2
Returns time-series equity data for charting the bot's portfolio value over time.
curl https://cymetica.com/api/v1/backtest/bots/alpha-momentum-v2/equity
Query Parameters
curl "https://cymetica.com/api/v1/backtest/bots/alpha-momentum-v2/trades?limit=10"
Bot Operations
Run backtests and update settings. These endpoints require authentication.
Triggers a new backtest run for the specified bot (Bearer token; no request body — the bot's own strategy, top-10 asset universe and a 30-day window are used). Responds immediately with {"run_id", "status": "queued", "slug"}; the refreshed results appear on the bot's profile and the leaderboard when the async run completes. Also callable as the MCP tool et_backtest_bot_run.
curl -X POST https://cymetica.com/api/v1/backtest/bots/my-bot/run-backtest \
-H "Authorization: Bearer YOUR_TOKEN"
Request Body
curl -X PATCH https://cymetica.com/api/v1/backtest/bots/my-bot/settings \
-H "Authorization: Bearer YOUR_TOKEN" \
-H "Content-Type: application/json" \
-d '{"name": "Alpha Bot v3"}'
Bot Cloning
Clone bot species into new instances. Cloned bots get dedicated HD wallets (account 4 derivation path). Requires authentication.
Request Body
curl -X POST https://cymetica.com/api/v1/backtest/clone \
-H "Authorization: Bearer YOUR_TOKEN" \
-H "Content-Type: application/json" \
-d '{"species_slug": "momentum-species", "name": "My Momentum Clone"}'
Returns deposit address and minimum deposit required to activate a cloned bot.
curl https://cymetica.com/api/v1/backtest/clone/deposit-info/momentum-species \
-H "Authorization: Bearer YOUR_TOKEN"
Paper Trading
View paper trades and paper trading status for bots running in simulation mode.
Query Parameters
open, closed, allcurl "https://cymetica.com/api/v1/backtest/bots/alpha-bot/paper-trades?status=open&limit=20"
Returns current paper trading status including P&L, open positions, and account balance.
curl https://cymetica.com/api/v1/backtest/bots/alpha-bot/paper-status
WebSocket — Real-Time Backtest Updates
Stream real-time backtest progress and results via WebSocket.
Message Types
// JavaScript WebSocket example
const ws = new WebSocket("wss://cymetica.com/ws/backtest/bot-123?run_id=run-456");
ws.onmessage = (event) => {
const msg = JSON.parse(event.data);
switch (msg.type) {
case "progress":
console.log(`${msg.percent}% — ${msg.step}`);
break;
case "completed":
console.log("Results:", msg.results);
break;
case "failed":
console.error("Error:", msg.error);
break;
}
};
Rate Limits
MCP Tools
All backtest endpoints are available as MCP tools for AI integration via the installable EventTrader MCP server (pip install cymetica-eventtrader-mcp) — these tool names come from that server. The hosted discovery endpoint at /.well-known/mcp exposes the public market-data toolset and does not include the backtest tools.