Run Your First Algotrading Strategy
A complete walkthrough — from never having traded crypto to a paper-traded bot running 24/7 on a server you control. Budget about 60 minutes for the first run; once you've done it once, the next bot takes 5 minutes.
We will:
- Create a Binance account and get it funded.
- Generate exchange API keys for the bot to use.
- Rent a small server (VPS) and harden it.
- Whitelist the server's IP on Binance.
- Install the
tradectlCLI. - Install a real, production-grade strategy (
shot). - Set up a Telegram bot for notifications.
- Write a config file and start the bot in paper mode.
- Watch it trade on the live monitor and in Telegram.
- Flip one switch to go live with real money.
At the end you will have an isolated, restartable, monitored algo trader running on a machine you own, taking simulated XRP trades on Binance Coin-Margined Futures (COIN-M).
A note on risk. This guide ends with paper trading on purpose. Algo trading can and will lose money. Run paper-mode for at least a week before risking a single dollar. Then start with the minimum order size your exchange allows. The bot will not make you rich — but a careless one can drain an account in an afternoon.
What you'll need
| Item | Notes |
|---|---|
| Email + phone | For Binance signup and 2FA |
| Government ID | For KYC (passport, driver's license, or national ID) |
| Credit/debit card or crypto wallet | To deposit ~$50 USDT for testing |
| VPS budget | ~$5–10/month |
ssh on your local machine | Built into macOS and Linux; on Windows use WSL or PuTTY |
| About 60 minutes | Mostly waiting for KYC verification |
Region check. Binance is not available to users in the United States — US residents must use Binance.US (different product, no Coin-M futures). The rest of this guide assumes Binance.com.
Part 1 — Create a Binance account
1.1 Sign up
- Open https://www.binance.com and click Register.
- Use a real email address you control. Pick a strong password.
- Verify the email code, then add your phone and verify the SMS code.
1.2 Pass KYC ("Verify Identity")
Binance will not let you trade futures (or use API keys for trading) without KYC.
- From the user menu pick Identification.
- Choose your country and the document type you have (passport is fastest).
- Take a photo of the document and a selfie when prompted.
- Wait. Most users are verified within 10 minutes; some take a few hours.
You can move on to Parts 2–4 while you wait.
1.3 Enable 2FA
Once KYC is approved:
- Security → Two-Factor Authentication.
- Add Authenticator App (Google Authenticator, Authy, 1Password, or similar). Save the recovery codes somewhere offline.
- Optionally add Security Key (YubiKey) for the strongest setting.
Why this matters. Even though our bot's API key won't be allowed to withdraw funds, a compromised Binance login gives an attacker total control. Treat 2FA recovery codes like cash.
1.4 Deposit USDT
You need stablecoin balance to convert to XRP for Coin-M margin.
- Wallet → Overview → Deposit.
- Pick USDT, then network TRC20 (cheapest) or BEP20 (slightly more expensive but fast).
- Deposit ~$50 worth — that's plenty for paper mode and a small live test later.
If you're buying from scratch, use Buy Crypto with a card. Fees are higher but it's one click.
1.5 Enable Futures and transfer funds
- Go to Derivatives → COIN-M Futures.
- Accept the futures user agreement (a 60-second questionnaire).
- From the Coin-M trading view, click Transfer. Move USDT from your Spot wallet to your Coin-M Futures wallet.
- In Coin-M, USDT can't be used as margin directly — you need the coin. Convert ~$30 of USDT to XRP, then transfer the XRP to the Coin-M Futures wallet.
You should now see an XRP balance under Coin-M Futures.
Part 2 — Create API keys
This is the credential the bot uses to read prices and place orders on your behalf. It is not your login password.
2.1 Create the key
- Account → API Management → Create API.
- Pick System generated.
- Name it
tradectl-xrp(or anything you'll recognize later). - Complete the 2FA challenge.
- Copy the API Key and Secret Key now, into a password manager. The Secret is shown exactly once. If you lose it, you must delete the key and create a new one.
2.2 Set restrictions
Click Edit restrictions on the new key:
- ✅ Enable Reading
- ✅ Enable Futures
- ❌ Enable Spot & Margin Trading — leave OFF (the bot doesn't need it)
- ❌ Enable Withdrawals — leave OFF, always
- ❌ Enable Universal Transfer — leave OFF
- IP whitelist: leave unrestricted for now — we'll come back here in Part 5 after we have a server IP.
Save.
Why "no withdrawals" matters. If your API key ever leaks (a compromised server, a logging mistake), the worst an attacker can do is open and close futures positions. They cannot drain your account. Never enable withdrawals on a bot key.
Part 3 — Rent a server (VPS)
The bot has to run somewhere that's always on. Your laptop is fine for testing but it'll miss trades every time it sleeps. A small Linux VPS is the standard answer.
Three good providers — pick one:
| Provider | Cost | Best for | Pay with |
|---|---|---|---|
| LightNode | ~$8/mo, hourly billing | Anyone who wants Asian regions close to Binance's matching engine, or who wants to pay in crypto | Card, USDT, BTC, ETH |
| Vultr | $6/mo "High Frequency" 1 vCPU / 1 GB | Easiest UX, broad region coverage, fastest support | Card, crypto |
| AWS Lightsail | $5/mo, 1 vCPU / 1 GB | Anyone already in the AWS ecosystem; very reliable | Card |
Region matters. Binance's primary matching engine is in Tokyo (ap-northeast-1). Picking a Tokyo region cuts ~150ms of round-trip latency vs. EU/US, which matters for any strategy that competes for fills. Recommendation:
- LightNode → Tokyo or Hong Kong
- Vultr → Tokyo or Singapore
- AWS Lightsail → Tokyo (ap-northeast-1)
Spec to pick: 1 vCPU, 1 GB RAM, 25 GB SSD, Ubuntu 24.04 LTS. That's plenty for one bot with a handful of pairs.
After you create the instance:
- Note the public IPv4 address. You'll need it twice — once on Binance, once when SSH'ing in.
- Note the SSH credentials. Most providers give you either:
- A root password (LightNode default), or
- An SSH key pair you upload (Vultr, AWS default — strongly preferred).
SSH keys vs. passwords. If your provider offers it, paste your public key (
~/.ssh/id_ed25519.pubfrom your local machine) into the provider's "SSH keys" UI before launching the VPS. Thenssh root@<IP>just works, with no password to brute-force. If you've never made an SSH key:ssh-keygen -t ed25519 -C "you@example.com"on your local terminal, accept defaults.
Part 4 — First login and basic hardening
From your local terminal:
ssh root@<YOUR_SERVER_IP>Accept the host key fingerprint. You're in.
A few one-time steps so we're not running as root forever:
# Create a non-root user
adduser trader
usermod -aG sudo trader
# Copy your SSH key over (so you can log in as `trader` later)
rsync --archive --chown=trader:trader ~/.ssh /home/trader
# Quick OS update
apt update && apt upgrade -y
# Basic firewall: SSH + lab monitor port only
apt install -y ufw
ufw allow OpenSSH
ufw allow 9200/tcp
ufw --force enable
# Switch to the new user
exit
ssh trader@<YOUR_SERVER_IP>You're now logged in as trader, the box is patched, and only ports 22 (SSH) and 9200 (the monitoring dashboard, Part 12) are reachable from the internet.
Part 5 — Whitelist the server on Binance
Now that you have a stable IP, lock the API key to it.
- Back on Binance → API Management → click Edit restrictions on the
tradectl-xrpkey. - Under Restrict access to trusted IPs only, paste your VPS's public IPv4 address.
- Save. Complete 2FA.
It takes up to ~10 minutes for the IP whitelist to propagate. If you run the bot too soon you'll see
Invalid API-key, IP, or permissions for action. Make a coffee, then carry on.
Part 6 — Install the tradectl CLI
Still SSH'd in as trader:
curl -fsSL https://tradectl.com/install.sh | sh
source ~/.bashrc
tradectl --versionYou should see something like tradectl 0.1.8. If the tradectl command isn't found, log out and back in (exit then ssh trader@...) so the new PATH is loaded.
The installer dropped one binary at ~/.tradectl/bin/tradectl and added it to your shell's PATH. No system-level changes, no daemons — just a single binary you own.
Part 7 — Sign in
The CLI needs an API key (different from your Binance API key — this one is for the tradectl service) so it can verify your license and upload trade history to your account on the dashboard.
- On your laptop, open https://app.tradectl.com and sign in with GitHub.
- Account → API Keys → Create. Name it after the server, e.g.
xrp-tokyo-vps. Copy thest_live_…value once. - Back on the VPS:
echo "st_live_xxxxxxxxxxxxxxxxxxxxxxxx" | tradectl loginVerify:
tradectl statusYou should see "authenticated" and your account email. The license JWT lives at ~/.tradectl/license.jwt and auto-refreshes; you do not need to log in again unless you rotate keys.
Part 8 — Install the shot strategy
shot is a counter-trend scalping strategy — it places a limit order slightly below the current price (for longs), follows the price as it moves, and exits at a small fixed take-profit. It's well-suited to liquid futures pairs that mean-revert on short timescales.
Install the prebuilt binary from the marketplace:
tradectl install shot
tradectl stratsThe second command lists every installed strategy. You should see shot with the path to its compiled .so (Linux) or .dylib (macOS). That .so is what gets loaded dynamically when you run the bot.
Want to compile from source instead? See strategies and the getting-started guide. The CLI install path is more than enough for this tutorial.
Part 9 — Set up the Telegram bot
The bot can push notifications to a Telegram chat (fills, P&L, errors) and accept commands back (/status, /stop, /positions, etc.). Two pieces are needed: a bot token and your chat ID.
9.1 Create the bot
- In Telegram, open a chat with @BotFather.
- Send
/newbot. - Give it any display name (e.g. XRP Trader).
- Give it a username ending in
bot(e.g.your_xrp_trader_bot). - BotFather replies with a token — a string like
8625226199:AAGb4.... Copy it.
9.2 Get your chat ID
- Search for @userinfobot in Telegram.
- Send
/start. It replies with your numeric ID (e.g.593295079). - Copy that too.
9.3 Activate the bot
Send /start to your own bot (the one BotFather just created). Without this first message, the bot can't message you back — Telegram blocks unsolicited outbound DMs.
You now have:
- A bot token:
8625226199:AAGb4... - A chat ID:
593295079
Both go in the config in the next part.
Part 10 — Write the config
On the VPS:
mkdir -p ~/bots/xrp-shot && cd ~/bots/xrp-shot
nano config.jsonPaste this, replacing the placeholders. config.json is strict JSON — no comments, no trailing commas. Each block is explained in the table that follows.
{
"telegram": {
"bot_token": "8625226199:AAGb4_REPLACE_WITH_YOUR_TOKEN",
"chat_id": "593295079_REPLACE_WITH_YOUR_CHAT_ID",
"send_interval": 10
},
"api": {
"provider": "Binance",
"key": "YOUR_BINANCE_API_KEY",
"secret": "YOUR_BINANCE_API_SECRET"
},
"limits": {
"maxLossLimit": 50
},
"db": { "path": "./data/orders.db" },
"log": {
"path": "./logs",
"mode": "console_file",
"level": "info"
},
"monitor": { "host": "0.0.0.0", "port": 9100 },
"strats": [
{
"name": "xrp-shot-demo",
"type": "shot",
"marketType": "INVERSE",
"isEmulator": true,
"pairs": ["XRPUSD_PERP"],
"direction": "LONG",
"entryDistance": 0.4,
"chaseSensitivity": 0.3,
"takeProfit": 0.1,
"stopLoss": 0.3,
"orderSize": 1
}
]
}What each top-level block does:
| Block | Purpose |
|---|---|
telegram | Bot token + chat ID from Part 9. send_interval is the notification batching window in seconds. |
api | Binance credentials from Part 2. The key is restricted to your VPS IP (Part 5). |
limits.maxLossLimit | Bot kills itself if hourly realized P&L drops below -$50. |
db.path | SQLite (WAL mode) for order persistence. |
log | console_file writes to both stdout and ./logs/*.log. Set level to debug for verbose output. |
monitor | WebSocket port the Lab dashboard reads from (Part 12). |
strats | Array — you can run multiple strategies in one bot. |
What each field in the strategy block means:
| Field | Value here | What it does |
|---|---|---|
name | xrp-shot-demo | Free-form label. Shows in logs and Telegram. |
type | shot | Matches the installed binary from Part 8. |
marketType | INVERSE | Coin-margined futures. (Use LINEAR for USDT-margined pairs like XRPUSDT.) |
isEmulator | true | Paper mode. Reads real market data, simulates fills. No real orders are sent. |
pairs | ["XRPUSD_PERP"] | Binance Coin-M XRP perpetual symbol. |
direction | LONG | Only opens long positions. Set SHORT for shorts. |
entryDistance | 0.4 | Place the entry limit 0.4% below current price. |
chaseSensitivity | 0.3 | Re-place the entry if price moves closer than 0.3% to it (i.e. chase the price down). Auto-clamped ≤ entryDistance. |
takeProfit | 0.1 | Close the position at +0.1% from entry. |
stopLoss | 0.3 | Force-exit if price drops 0.3% below entry. |
orderSize | 1 | One contract per entry. In Coin-M, orderSize is in base asset (XRP), not USD. Worst-case loss on this single open trade ≈ 0.3% × 1 XRP × price ≈ a few cents. |
Save and exit nano (Ctrl-O, Enter, Ctrl-X).
Validate the file before running:
tradectl config validate config.jsonYou should see config OK. If you get an error, the message will point at the offending field — usually a missing comma or quote.
Part 11 — Run it
tradectl run config.json --daemon--daemon detaches the bot from your terminal so it keeps running after you close the SSH session.
Check status and tail logs:
tradectl status
tradectl logs -fA healthy startup looks something like:
[info] connected to Binance Coin-M REST
[info] connected to Binance Coin-M public WebSocket
[info] connected to user-data stream (private WS)
[info] strategy xrp-shot-demo loaded — pairs=[XRPUSD_PERP], emulator=true
[info] monitor server listening on 0.0.0.0:9200 → ws 0.0.0.0:9100
[info] ready, waiting for ticker events…Within a couple of minutes a Telegram message should arrive — at minimum the bot started notification. As XRP moves, entries will trigger and you'll see placeEntry / editEntry / fill events stream by.
Press
Ctrl-Cto detach from the log tail. The bot stays running.
Part 12 — Watch it work
12.1 Lab dashboard (coming soon)
Open in your laptop browser:
http://<YOUR_SERVER_IP>:9200You'll see the local Lab dashboard. Go to Monitor. The page WebSocket-connects to the bot and shows:
- Live ticker per pair
- Active orders and their distance from market
- Open positions with TP/SL lines
- A running fills/P&L feed
This works identically for paper and live runs.
12.2 Telegram commands
Open the bot's chat in Telegram and try:
| Command | What it does |
|---|---|
/help | List every command |
/status | Uptime, active strategies, open positions |
/positions | All open positions with their TPs and SLs |
/profit | Today's realized P&L |
/month | Day-by-day P&L for the current month (USDT) |
/month_coins | Same, but in base asset |
/detailed | Breakdown by strategy and by pair |
/last_month, /last_month_coins, /detailed_last | Same for the previous month |
/stop | Graceful shutdown — cancels open entries, leaves TP/SL on the exchange so any position stays protected |
12.3 Did it actually do anything?
Paper-mode runs don't appear on Binance — there are no real orders. You'll see activity in:
- Telegram messages (every fill)
~/bots/xrp-shot/logs/*.log~/bots/xrp-shot/data/orders.db(a SQLite file you can inspect)- The Lab dashboard's monitor view
- Your dashboard at app.tradectl.com/dashboard/trades, once the bot pushes its trade reporter batch (every ~5 seconds)
Part 13 — Going live (requires closed alpha access)
Leave the bot in paper mode for at least a week. Confirm that:
- It survives Binance disconnects without crashing (check
tradectl logs -n 500 | grep -iE 'error|reconnect'). - It restarts cleanly:
tradectl stop && tradectl run config.json --daemon. - Its paper P&L over the period is at least not visibly negative. Paper-mode P&L is optimistic — slippage and queue position aren't fully simulated — so a paper-mode loser is a near-certain live loser.
When you're ready to go live, change exactly one field:
"isEmulator": falseThen restart:
tradectl stop
tradectl run config.json --daemonWatch tradectl logs -f for the first real fill. The bot will print a PLACED ENTRY line followed by a Telegram notification with the order ID. You can cross-check on Binance under Coin-M Futures → Open Orders.
Start with
orderSize: 1(one XRP contract). On a $0.60 XRP that's a notional position of $0.60. You will not get rich. You will also not get poor. After a week of stable behavior, scale.
When things go wrong
| Symptom | Cause | Fix |
|---|---|---|
Invalid API-key, IP, or permissions for action | VPS IP isn't whitelisted, or you whitelisted < 10 min ago | Wait, then re-check the IP in API Management |
Margin is insufficient | No XRP balance in the Coin-M Futures wallet | Convert USDT → XRP, then Transfer to Coin-M |
Plugin ABI version mismatch | Strategy binary was built against an older SDK | tradectl install shot again — the installer fetches the matching binary |
license invalid or unable to verify license | Token expired, or you rotated the st_live_ key | tradectl login again with a fresh key from app.tradectl.com |
Repeated Connection reset / EAI_AGAIN errors | Binance blocks the VPS region (e.g. US-based VPS) | Move the VPS to Tokyo / Singapore / Hong Kong / EU |
| Telegram messages never arrive | You never sent /start to your own bot | Open the bot chat in Telegram and send /start once |
tradectl status says "running" but logs show no fills | Strategy is gated (e.g. session limits, edge decay) | Try /session_reset ALL in Telegram, or check tradectl logs -f for gating reasons |
| Bot exits unexpectedly | Daily max-loss hit, or 3+ persistent errors in 60s | Check tradectl logs -n 200 for the shutdown reason. Errors like -2019 (margin) or -2027 (qty exceeded) self-stop the strategy by design |
Monitor dashboard shows disconnected | Lab can't reach port 9100 on the bot | Both run on the same host in this guide; restart the bot. If you ever split them, open 9100 in ufw to the lab host |
For deeper issues, run with debug logs and share with support:
# Edit config.json: "log": { "level": "debug" }
tradectl stop && tradectl run config.json --daemon
tradectl logs -n 500 > debug.logNext steps
Now that you have one bot running, here's where to go:
- Backtest before live: Backtesting →. Run
shotagainst months of historical data before risking capital. - Sweep parameters: Optimization →. Find which
entryDistance/takeProfitcombo works best for XRP. - Manage running bots: Deployment →. Multiple bots per server, restart policies, log rotation.
- Add more pairs and strategies: Strategies →. Run several strategies and pairs from one config — they isolate cleanly.
- More exchanges: Exchanges →. Bybit, OKX, Hyperliquid, HTX, Gate, and Bitget are supported with the same config shape; only the
api.providerfield changes.
Welcome to algotrading.
