The CuteMarkets Paper Trading API is a local simulator similar to the one Alpaca has. It accepts Alpaca-shaped order payloads, but it does not route orders to Alpaca and it does not require Alpaca credentials.
Use this page with Paper Trading, Paper Trading Bot Data Stack, Paper Trading Bot Operations, Backtest to Paper Trading Parity Checklist, and Backtest vs Paper Trading Live Drift.
Use a Paper Trading API key for these endpoints:
Authorization: Bearer cm_your_paper_key
AI Agent Quick Start
Use this flow when an agent needs to start paper trading from zero:
- List accounts and pick one if it exists.
- Create one if the list is empty.
- Submit orders with a stable
client_order_id. - Poll orders, positions, and portfolio history after every decision.
BASE_URL="https://api.cutemarkets.com/v1"
PAPER_KEY="cm_your_paper_key"
ACCOUNT_ID=$(
curl -s "$BASE_URL/paper/accounts/" \
-H "Authorization: Bearer $PAPER_KEY" |
python -c 'import json,sys; rows=json.load(sys.stdin)["results"]; print(rows[0]["id"] if rows else "")'
)
if [ -z "$ACCOUNT_ID" ]; then
ACCOUNT_ID=$(
curl -s "$BASE_URL/paper/accounts/" \
-X POST \
-H "Authorization: Bearer $PAPER_KEY" \
-H "Content-Type: application/json" \
-d '{"name":"agent-sandbox","initial_cash":"100000"}' |
python -c 'import json,sys; print(json.load(sys.stdin)["account"]["id"])'
)
fi
curl "$BASE_URL/paper/accounts/$ACCOUNT_ID/orders/" \
-X POST \
-H "Authorization: Bearer $PAPER_KEY" \
-H "Content-Type: application/json" \
-d '{
"symbol": "AAPL",
"qty": "1",
"side": "buy",
"type": "market",
"time_in_force": "day",
"client_order_id": "agent-aapl-001"
}'
Recommended agent loop:
- Use one account per strategy or experiment.
- Never reuse a
client_order_idinside the same account generation. - Read
/orders/,/positions/, and/portfolio/history/before making the next decision. - Use
DELETE /orders/{order_id}/to cancel any opennew,accepted, orpartially_filledorder. - Orders submitted while the regular market is closed stay
accepteduntil the next regular session, so agents can cancel them before they are evaluated. - Use
POST /reset/only when intentionally starting a new run.
If the paper strategy uses market data, connect each order decision back to Options Backtesting API, Backtesting Execution Realism, Stock Trades and Quotes, and Options Chain Scanner Architecture. That keeps paper fills, quote windows, reject reasons, and live drift reviewable.
Accounts
Users can keep up to 20 active paper accounts. Archived accounts do not count toward that limit.
curl https://api.cutemarkets.com/v1/paper/accounts/ \
-H "Authorization: Bearer cm_your_paper_key"
Create an account:
curl https://api.cutemarkets.com/v1/paper/accounts/ \
-X POST \
-H "Authorization: Bearer cm_your_paper_key" \
-H "Content-Type: application/json" \
-d '{
"name": "ORB Sandbox",
"initial_cash": "100000"
}'
Reset an account:
curl https://api.cutemarkets.com/v1/paper/accounts/{account_id}/reset/ \
-X POST \
-H "Authorization: Bearer cm_your_paper_key" \
-H "Content-Type: application/json" \
-d '{
"confirm": true,
"initial_cash": "100000",
"reason": "new strategy run"
}'
Resetting cancels open orders, clears current positions, starts a new account generation, and preserves prior orders, fills, ledger entries, and equity history for audit.
Rename an account:
curl https://api.cutemarkets.com/v1/paper/accounts/{account_id}/ \
-X PATCH \
-H "Authorization: Bearer cm_your_paper_key" \
-H "Content-Type: application/json" \
-d '{"name": "agent-run-2026-05-16"}'
Delete an account from the active list:
curl https://api.cutemarkets.com/v1/paper/accounts/{account_id}/ \
-X DELETE \
-H "Authorization: Bearer cm_your_paper_key"
Delete archives the account. It is hidden from the default account list, but remains available in audit history through ?include_archived=true.
Orders
Submit an order:
curl https://api.cutemarkets.com/v1/paper/accounts/{account_id}/orders/ \
-X POST \
-H "Authorization: Bearer cm_your_paper_key" \
-H "Content-Type: application/json" \
-d '{
"symbol": "AAPL",
"qty": "10",
"side": "buy",
"type": "market",
"time_in_force": "day",
"client_order_id": "strategy-aapl-001"
}'
Submit a single-leg option order:
curl https://api.cutemarkets.com/v1/paper/accounts/{account_id}/orders/ \
-X POST \
-H "Authorization: Bearer cm_your_paper_key" \
-H "Content-Type: application/json" \
-d '{
"symbol": "O:SPY260620C00500000",
"qty": "1",
"side": "buy",
"type": "limit",
"limit_price": "4.25",
"time_in_force": "day",
"position_intent": "buy_to_open"
}'
Look up an order by client id:
curl "https://api.cutemarkets.com/v1/paper/accounts/{account_id}/orders:by_client_order_id?client_order_id=strategy-aapl-001" \
-H "Authorization: Bearer cm_your_paper_key"
Cancel an open order:
curl https://api.cutemarkets.com/v1/paper/accounts/{account_id}/orders/{order_id}/ \
-X DELETE \
-H "Authorization: Bearer cm_your_paper_key"
The dashboard uses the same endpoint. Open orders show a Cancel action in the Paper Trading orders table.
Supported v1 order behavior:
| Field | Supported |
|---|---|
symbol | Stock tickers and O: option contract tickers |
qty | Decimal stock quantities; whole option contract quantities |
side | buy, sell |
type | market, limit |
time_in_force | Stocks: day, gtc; options: day |
position_intent | Options: buy_to_open, sell_to_close |
client_order_id | Optional, unique per account generation |
Rejected in v1: stock short openings, naked option sells, multileg orders, option fractional quantities, notional orders, stop orders, trailing-stop orders, and extended-hours option orders.
Realism Model
The simulator uses conservative quote-aware fills:
- Stock buys fill at ask and sells fill at bid.
- Option buys fill at ask and sells fill at bid, with a 100 multiplier.
- Limit orders fill only when marketable against the latest quote.
- Missing, crossed, stale, or invalid quotes prevent fills.
- Wide option spreads are rejected.
- Opening trades must fit available paper cash.
- Regular market hours are required for v1 fills. Orders submitted while the market is closed remain accepted and are evaluated during the next regular session unless canceled first.
Performance
Portfolio history is available as an equity time series:
curl https://api.cutemarkets.com/v1/paper/accounts/{account_id}/portfolio/history/ \
-H "Authorization: Bearer cm_your_paper_key"
The dashboard uses the same data for equity, cash, market value, realized P&L, unrealized P&L, drawdown, and recent fill charts.
Paper API implementation notes
Paper trading needs separate credentials, account state, order state, position state, and fill evidence. Store account id, client_order_id, symbol, side, quantity, order type, time in force, position intent, submitted time, accepted time, fill time, and reject reason. For options, also store the quote or snapshot evidence used before the order was submitted.
Use Paper Trading Bot Data Stack and Paper Trading Bot Operations when connecting research to paper runs. A paper order that fills without the same data-feed policy as the backtest cannot validate strategy parity. Keep paper resets explicit so old positions and new experiments do not share an account generation by accident.
Additional implementation review
Review the paper trading API workflow as a sequence of named data objects, not as a single helper call. The implementation should preserve paper account id, buying power, position intent, time in force, client order id, order status, fill price, and cancel state. Those fields make support tickets, CI fixtures, and replay notebooks easier to compare because every step can point to the exact request and response that created the displayed value.
The main failure mode is that a simulator can accept an order shape that no review process can connect back to the market data decision. Before promoting the workflow, run one concrete example through discovery, retrieval, display, logging, and error handling. Keep the resulting artifact beside the code path so future changes can prove they still use the same terminology and the same market-data assumptions.