Trader
Tools

Quickstart

Create an API key, connect a master and a follower account, create a copier and attach the follower, then check that it's copying.

View as Markdown

This guide takes about ten minutes, most of it waiting for two MetaTrader terminals to start. You will connect two accounts, copy the trades of one to the other, and read back the follower's status and the copier's events.

You need a plan with at least two account slots and two MetaTrader 4 or 5 accounts: one whose trades are copied (the master) and one that copies them (the follower). Demo accounts work.

The examples use cURL with jq, TypeScript with the built-in fetch of Node.js 18 or later, and Python with the requests package.

1. Create an API key

  1. Sign in at app.algotradertools.com.
  2. Open API keys in the sidebar and create a key. Leave all four scopes selected.
  3. Copy the key. It is shown only once.

2. Export the key

Keep the key out of your source code. The examples read it from an environment variable:

export ATT_API_KEY="att_…"

The TypeScript and Python examples share a small helper that sends the key, encodes JSON and turns error responses into exceptions. Save it next to your script:

// att.ts
const API = "https://api.algotradertools.com/v1";

export async function att(method: string, path: string, body?: unknown) {
  const response = await fetch(`${API}${path}`, {
    method,
    headers: {
      Authorization: `Bearer ${process.env.ATT_API_KEY}`,
      ...(body === undefined ? {} : { "Content-Type": "application/json" }),
    },
    body: body === undefined ? undefined : JSON.stringify(body),
  });
  if (response.status === 204) return null;
  const payload = await response.json();
  if (!response.ok) {
    throw new Error(`${payload.code}: ${payload.detail} (request ${payload.request_id})`);
  }
  return payload;
}

Put the TypeScript examples in a file such as quickstart.ts and run it with npx tsx quickstart.ts.

3. Connect the master and the follower

Connect the master with its investor (read-only) password, since its trades only need to be read. The follower receives trades, so it needs its master (trading) password. Each password is stored encrypted with the terminal that runs the account and is never shown again.

curl https://api.algotradertools.com/v1/accounts \
  -H "Authorization: Bearer $ATT_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "platform": "mt5",
    "server": "ICMarketsSC-Demo",
    "login": 51234567,
    "password": "<investor password>",
    "credential_kind": "investor",
    "nickname": "Gold master"
  }'

curl https://api.algotradertools.com/v1/accounts \
  -H "Authorization: Bearer $ATT_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "platform": "mt5",
    "server": "ICMarketsSC-Demo",
    "login": 51239876,
    "password": "<master password>",
    "credential_kind": "master"
  }'

Each request returns 201 Created with the new account, still in connecting:

{
  "id": "4f6c2a1e-8b3d-4e7a-9c5f-1d2e3a4b5c6d",
  "object": "account",
  "name": "Gold master",
  "nickname": "Gold master",
  "platform": "mt5",
  "server": "ICMarketsSC-Demo",
  "login": 51234567,
  "credential_kind": "investor",
  "can_trade": false,
  "status": "connecting",
  "error": null,
  "released": false,
  "role": null,
  "figures": null,
  "created_at": "2026-10-25T14:03:51.204Z"
}

Copy the server name exactly as MetaTrader shows it in its login window. A wrong server name fails with 400 server_not_found, and a wrong password with 400 invalid_credentials.

4. Wait until both are connected

Each terminal starts and logs in to the broker, which takes two to three minutes. Check the account every 15 seconds or less often until its status is connected. If it turns to error instead, the error field says why.

MASTER_ID=4f6c2a1e-8b3d-4e7a-9c5f-1d2e3a4b5c6d
FOLLOWER_ACCOUNT_ID=9b2e7d4c-1a3f-4c8e-b5d6-7e8f9a0b1c2d

for id in $MASTER_ID $FOLLOWER_ACCOUNT_ID; do
  until [ "$(curl -s https://api.algotradertools.com/v1/accounts/$id \
    -H "Authorization: Bearer $ATT_API_KEY" | jq -r .status)" != "connecting" ]; do
    sleep 15
  done
done

5. Create a copier

A copier watches its master and copies the master's trades to its followers. Create one for the master you just connected:

curl https://api.algotradertools.com/v1/copiers \
  -H "Authorization: Bearer $ATT_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "name": "Gold strategy", "master_id": "'$MASTER_ID'" }'
{
  "id": "c7d1e5f2-3a4b-4c6d-8e9f-0a1b2c3d4e5f",
  "object": "copier",
  "name": "Gold strategy",
  "is_active": true,
  "master_id": "4f6c2a1e-8b3d-4e7a-9c5f-1d2e3a4b5c6d",
  "master": {
    "id": "4f6c2a1e-8b3d-4e7a-9c5f-1d2e3a4b5c6d",
    "name": "Gold master",
    "platform": "mt5",
    "server": "ICMarketsSC-Demo",
    "login": 51234567,
    "status": "connected"
  },
  "followers": [],
  "open_copies": 0,
  "created_at": "2026-10-25T14:08:30.512Z",
  "updated_at": "2026-10-25T14:08:30.512Z"
}

6. Attach the follower

Attach the follower account and give it the rules it should copy with. The follower below sizes its lots by its equity compared with the master's, trades at most 2 lots per copy, and only copies XAUUSD on weekdays from 07:00 to 21:00 London time. Every rule you leave out keeps its default.

COPIER_ID=c7d1e5f2-3a4b-4c6d-8e9f-0a1b2c3d4e5f

curl https://api.algotradertools.com/v1/copiers/$COPIER_ID/followers \
  -H "Authorization: Bearer $ATT_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "account_id": "'$FOLLOWER_ACCOUNT_ID'",
    "lot_mode": "equity_ratio",
    "lot_value": 1,
    "max_lot": 2,
    "symbol_filter": "include",
    "symbols": ["XAUUSD"],
    "sessions": [{ "days": [0, 1, 2, 3, 4], "start": "07:00", "end": "21:00" }],
    "timezone": "Europe/London"
  }'

The response is the new follower, with every rule filled in. Its status is null until the copier engine first reports on it, usually within a few seconds:

{
  "id": "e2f4a6b8-c0d2-4e46-8a8c-9e0f1a2b3c4d",
  "object": "follower",
  "copier_id": "c7d1e5f2-3a4b-4c6d-8e9f-0a1b2c3d4e5f",
  "account_id": "9b2e7d4c-1a3f-4c8e-b5d6-7e8f9a0b1c2d",
  "account": {
    "id": "9b2e7d4c-1a3f-4c8e-b5d6-7e8f9a0b1c2d",
    "name": "MT5 51239876",
    "platform": "mt5",
    "server": "ICMarketsSC-Demo",
    "login": 51239876,
    "status": "connected"
  },
  "is_active": true,
  "magic": 1840273951,
  "lot_mode": "equity_ratio",
  "lot_value": 1,
  "adjust_contract_size": true,
  "below_minimum": "minimum",
  "max_lot": 2,
  "reverse": false,
  "copy_stops": true,
  "max_slippage_pips": null,
  "max_delay_seconds": 60,
  "copy_existing": false,
  "symbol_filter": "include",
  "symbols": ["XAUUSD"],
  "sessions": [{ "days": [0, 1, 2, 3, 4], "start": "07:00", "end": "21:00" }],
  "timezone": "Europe/London",
  "symbol_map": {},
  "status": null,
  "created_at": "2026-10-25T14:09:02.118Z",
  "updated_at": "2026-10-25T14:09:02.118Z"
}

Positions the master already had open aren't copied unless you set copy_existing. Without it, only what the master opens from now on is copied.

7. Check that it's copying

Read the copier. Each of its followers has a live status from the copier engine:

curl https://api.algotradertools.com/v1/copiers/$COPIER_ID \
  -H "Authorization: Bearer $ATT_API_KEY" | jq '.followers[] | {account: .account.name, status}'
{
  "account": "MT5 51239876",
  "status": {
    "state": "copying",
    "message": "",
    "master_connected": true,
    "follower_connected": true,
    "open_copies": 0,
    "last_event_at": null,
    "balance": 5000.0,
    "equity": 5031.2,
    "currency": "USD",
    "heartbeat_at": "2026-10-25T14:09:20.004Z",
    "engine_online": true
  }
}

Now open a gold trade on the master. Within a second or so, the copy shows up in the copier's events, which are listed newest first:

curl "https://api.algotradertools.com/v1/copiers/$COPIER_ID/events?limit=5" \
  -H "Authorization: Bearer $ATT_API_KEY"
{
  "object": "list",
  "data": [
    {
      "id": 48213,
      "object": "copy_event",
      "follower_id": "e2f4a6b8-c0d2-4e46-8a8c-9e0f1a2b3c4d",
      "account_id": "9b2e7d4c-1a3f-4c8e-b5d6-7e8f9a0b1c2d",
      "master_ticket": 3518820446,
      "action": "open",
      "ok": true,
      "message": "Opened 0.48 XAUUSD (buy) at 2391.84.",
      "detail": {
        "symbol": "XAUUSD",
        "side": "buy",
        "volume": 0.48,
        "stopLoss": 2380.0,
        "takeProfit": null,
        "price": 2391.84,
        "retcode": 10009,
        "outcome": "applied",
        "ticket": 3518820991
      },
      "received_at": "2026-10-25T14:21:07.211Z",
      "engine_ms": 0.31,
      "execution_ms": 186.4,
      "total_ms": 186.7
    }
  ],
  "has_more": false,
  "next_cursor": null
}

The master traded 1 lot with 10,318.40 USD equity. The follower has 5,031.20 USD equity, so it traded 1 × 5,031.20 ÷ 10,318.40 = 0.4876 lots, rounded down to the broker's lot step. That gives 0.48 lots.

If a request fails

Errors are JSON problem details with a code such as invalid_api_key, plan_limit_reached or validation_failed. For validation_failed, errors names each field that needs fixing. See Errors for every code.

8. Pause, resume and clean up

  • To pause one follower, send { "is_active": false } with PATCH /v1/copiers/{copier_id}/followers/{follower_id}. To pause the whole copier, send the same body with PATCH /v1/copiers/{copier_id}. Send true to resume. See Copiers.
  • Delete the copier with DELETE /v1/copiers/{copier_id}. Add ?close_positions=true to close the copies it opened as well.
  • Disconnect an account with DELETE /v1/accounts/{account_id} once no copier uses it.

Next steps

On this page