Paper-first AI trading terminal β Rust/axum + React, Alpaca, Kimi + local Gemma research, options bots, deterministic risk engine, Vanna DB chat. Ships as a web app (MySQL) and a native macOS app (embedded SQLite).
A Bloomberg-style, paper-first algorithmic trading terminal: a deterministic strategy + risk engine, AI market research, real-time charts, weekly options flow & contract selection, a natural-language chat over your own database, and a guided bot builder. Built on Alpaca for commission-free US equities/ETFs/options.
It ships in two forms from one codebase:
.app with an embedded SQLite database (no external DB needed).http://localhost:8001, backed by MySQL.The two stay in sync automatically (SQLite β MySQL).
The native macOS app (paper account, live Alpaca data).

Pick an outcome (Conservative β YOLO) or build from a documented strategy; one-click Add as Bot.

Set your starting cash and max bet per trade; get net P&L $, ending balance, equity curve and a per-trade ledger.

Every top-bar stat links to a dedicated page: equity β Portfolio, day P&L β P&L history, buying power β Buying Power.


P&L history (date-range, per-period histogram)![]() |
Buying Power (totals, reserved, education)![]() |
Options Flow![]() |
Guided Bot Builder![]() |
Trades ledger (plain-English contracts)![]() |
Positions & Orders (quick buy/sell)![]() |
AI Research (local Gemma + Kimi)![]() |
Chat over your DB (Vanna-style + RAG)![]() |
β οΈ Educational project β not financial advice. Automated trading can lose money rapidly. Paper/backtest results donβt guarantee live performance. The AI can be confidently wrong β thatβs why a deterministic risk engine has veto power over every order. Trade live only with money you can afford to lose.
The LLM proposes; deterministic code disposes. AI generates theses and signals, but a rule-based risk engine validates every order against hard limits before anything reaches the broker. AI is used for information processing (news/sentiment/regime), never as the last line of defense.
ββββββββββββββββββββββββββββββββββββββββββββββββ
β React + TypeScript + Vite frontend (SPA) β
β embedded into the Rust binary at build time β
βββββββββββββββββ¬βββββββββββββββββββββββββββββββ
β /api (REST) + /ws (WebSocket)
βββββββββββββββββΌβββββββββββββββββββββββββββββββ
β Rust / axum backend (backend-rs) β
β strategy Β· risk engine Β· options Β· bots Β· β
β research Β· Vanna chat Β· 24/7 worker Β· sync β
βββββ¬ββββββββββββββββ¬ββββββββββββββββ¬ββββββββββββ
β β β
ββββββββΌββββββ ββββββββΌβββββββ βββββββΌβββββββ
β Alpaca β β Kimi / β β MySQL or β
β (paper) β β Ollama β β SQLite β
β trading + β β (Gemma) β β (auto- β
β data + opt β β research+ β β synced) β
β + news β β chat β β β
ββββββββββββββ βββββββββββββββ ββββββββββββββ
The native macOS app wraps this same backend in a Tauri window using SQLite; the web build uses MySQL.
| Need | For | Install |
|---|---|---|
| Alpaca paper account + API keys | trading & market data | https://app.alpaca.markets (free) |
| Rust (stable) | the backend / native app | https://rustup.rs |
| Node.js 20+ | building the frontend | https://nodejs.org |
Ollama + gemma4:e2b |
free local AI (worker + chat) | https://ollama.com β ollama pull gemma4:e2b |
| MySQL (e.g. MAMP) | the web build & cross-sync | MAMP defaults: 127.0.0.1:8889, root/root |
| Kimi key (optional) | best on-demand research | https://platform.kimi.ai β omit to use free Gemma only |
| Tauri CLI (for the .app) | building the macOS app | cargo install tauri-cli or npm i -g @tauri-apps/cli |
The native macOS app needs no MySQL (it uses embedded SQLite). MySQL is only required for the web build and for cross-device sync.
git clone https://github.com/erichers/ai-trading-bot.git
cd ai-trading-bot
# 1) Configure secrets (never committed)
cp .env.example .env
# β edit .env: add your ALPACA_API_KEY / ALPACA_SECRET_KEY (required)
# and optionally KIMI_API_KEY (else research runs on free local Gemma)
# 2) Local AI (free)
ollama pull gemma4:e2b # and make sure `ollama serve` is running
# 3a) WEB build (needs MySQL running β e.g. start MAMP):
./run-native.sh # builds the frontend + Rust release, serves http://localhost:8001
# (creates the `trading_terminal` MySQL db if missing)
# 3b) NATIVE macOS app (embedded SQLite, no MySQL needed):
cd frontend && npm run build && cd ..
cd app-native/src-tauri && cargo tauri build --bundles app
open "target/release/bundle/macos/AI Trading Terminal.app"
Thatβs it β open http://localhost:8001 (web) or the .app (native).
./run-native.sh β ensures Ollama + MySQL, builds, runs on http://localhost:8001.cd frontend && npm run build then cd backend-rs && cargo run --release (defaults to DB_BACKEND=mysql).cd frontend && npm run dev (Vite on :5173, proxies to the backend on :8001).cd app-native/src-tauri && cargo tauri build --bundles app (build frontend/ first so the embedded UI is current).~/Library/Application Support/com.orcounselors.tradingterminal/trading_terminal.db.xattr -dr com.apple.quarantine "<app>").Trading Terminal.app on the Desktop (compiled from app-native/launcher/launcher.applescript):
trading_terminal. Native app β embedded SQLite. Identical schema (trades, research, deep research, signals, risk events, bots, strategies, watchlist, settingsβ¦).POST /api/sync; status: GET /api/sync/status.backend-rs/ Rust/axum backend (primary) β lib + binary; MySQL & SQLite; sync; embedded SPA
app-native/ Tauri macOS app (embedded SQLite) + Desktop launcher (AppleScript)
frontend/ React + TS + Vite SPA (built into the backend binary)
backend/ Original Python/FastAPI implementation (reference / alternative)
deploy/ Optional Apache vhost (legacy /sandbox serving)
run-native.sh One-command web launcher
.env.example Copy to .env and fill in your keys
.env (gitignored, never committed). The app reads them at runtime β they are not bundled into the binary or the .app. For a portable install, place credentials in ~/.config/trading-terminal/.env.ALPACA_PAPER_TRADE=true) until you deliberately switch to live keys.KIMI_API_KEY; Kimi reasoning models take ~60β90s (thereβs a spinner). Free Gemma always works if Ollama is running.ollama serve is up and gemma4:e2b is pulled.MIT. Provided for educational purposes only; not financial, investment, or trading advice. Stops and conditional orders are best-effort and can fail near the close or during outages. You are solely responsible for any trading decisions and losses.