rkang30/open-trade-bot

Free, open-source Next.js starter for a stock trading bot — wired to the Picckles Signals API, ships in paper-trading mode.

2

stars

4

commits

TypeScript

primary language

Aug 17, 2026

updated

picckles.com
algotrading
nextjs
open-source
stock-api
trading-bot-monitoring
typescript

README

open-trade-bot — a free Next.js trading-bot starter

open-trade-bot

A free, open-source Next.js starter for a stock trading bot — wired to a signals API, running itself on a daily cron. Ships in paper-trading mode.

License: MIT Next.js TypeScript Paper trading

Deploy with Vercel


Most "build a trading bot" tutorials either hand-wave the strategy ("insert your alpha here") or bury you in backtesting before you've written a line. This does the opposite: it treats the strategy as an external input (the Picckles Signals API, a read-only REST endpoint of daily buy/sell signals) and focuses on the engineering that actually trips people up — scheduling, persistence, idempotency, and deploy.

It ships in paper-trading mode so you can watch it work with zero broker setup. Going live is one function to swap (runTick in src/lib/bot.ts).

Architecture

Vercel Cron  (weekdays, 21:05 UTC — just after the US close)
      │
      ▼
GET /api/run ──► runTick(strategy)
                     │
                     ├─► picckles.ts   fetch SELL/HOLD on held positions, then today's BUY signals
                     ├─► bot.ts        resolve exits, size new entries to budget, skip symbols already held
                     └─► store.ts      persist positions + trade ledger to Upstash Redis
      ▲
      │
 Dashboard  ( / )  ──►  "Run now" button triggers a manual tick

What it does

Each tick (GET /api/run, hit by Vercel Cron or your own scheduler):

  1. Asks the API for SELL / HOLD decisions on any position it's currently holding, and paper-sells the SELLs.
  2. Asks the API for today's BUY signals, sizes them to your per-trade budget, and paper-buys anything new (skipping symbols it already owns). A crash gate can suppress new entries on high-VIX days.
  3. Persists positions and a trade ledger to Upstash Redis.

The dashboard (/) shows open positions and recent trades, with a Run now button to fire a tick manually — handy for trying it out without waiting for the cron.

How it's laid out

FileRole
src/app/api/run/route.tsThe cron/HTTP entry point — one tick per request
src/lib/bot.tsrunTick() — the whole trading loop (exits → entries → persist)
src/lib/picckles.tsThin fetch client for the signals API
src/lib/store.tsUpstash Redis: positions + trade ledger
src/app/page.tsx + RunButton.tsxThe dashboard and manual-run button
vercel.jsonThe daily cron schedule

Quickstart

git clone https://github.com/rkang30/open-trade-bot
cd open-trade-bot
npm install

cp .env.example .env.local
# - free API key:     https://picckles.com/api-pricing
# - free Upstash Redis (so positions persist): https://upstash.com

npm run dev

Open localhost:3000 and click Run now.

Deploying

  1. Push to GitHub, import into Vercel (or use the Deploy with Vercel button above).
  2. Add the env vars from .env.example (PICCKLES_API_KEY, UPSTASH_REDIS_REST_URL / _TOKEN, a random CRON_SECRET).
  3. vercel.json already schedules /api/run for 5 21 * * 1-5 (21:05 UTC, weekdays — shortly after the US close). Adjust to taste.

Strategies

Set STRATEGY in your env to either:

StrategyStyleTypical hold
double7-guarded (default)Buy a strong uptrend on a short-term low, with a VIX crash gate~2–3 weeks
rs-pullbackBuy a relative-strength leader on a fast capitulation dip~2–5 days

Full entry/exit rules: picckles.com/api-docs#strategies.

Going live

Everything routes through runTick() in src/lib/bot.ts, which currently only records paper trades via logTrade(). Add a real broker call (Alpaca, Interactive Brokers, etc.) alongside it and the rest of the bot — signal fetching, exit checks, position tracking — is unchanged. The signals client is a plain fetch, so pointing it at a different endpoint is a small edit too.

FAQ

Is it free? The code is MIT. The signals API and Upstash Redis both have free tiers, so you can run the whole thing at $0.

Do I need to know a trading strategy? No — that's the point. The API supplies the entry/exit decisions; this repo is the runnable wiring around them.

Does it place real trades? No. It's paper-trading by default — no broker keys, no real orders. Wiring a real broker is opt-in and on you (see Going live).

Can I use a different signals source or broker? Yes. src/lib/picckles.ts is a thin fetch client and runTick() is broker-agnostic — swap either without touching the core loop.

How does it avoid double-buying if a cron tick retries? Before buying, runTick() loads current positions from Redis and skips any symbol it already holds, and signals only change once per trading day — so re-running a tick (cron retry or the manual button) won't double-buy.

Why Redis instead of a database? Serverless functions are stateless; positions need to survive between invocations. Redis is the smallest thing that does that. Swap src/lib/store.ts for Postgres if you'd rather.

Learn how it's built

Step-by-step tutorial with the reasoning behind each piece: How to Build a Stock Trading Bot with Next.js and a Trading Signals API

Disclaimer

Signals are informational only and identical for every API subscriber — not personalized investment advice. This bot trades paper money by default; you are responsible for anything you connect to a real broker. Past performance does not predict future results.

License

MIT

Contributors

rkang30

4 commits

rkang30/open-trade-bot

Free, open-source Next.js starter for a stock trading bot — wired to the Picckles Signals API, ships in paper-trading mode.

2

stars

4

commits

TypeScript

primary language

Aug 17, 2026

updated

picckles.com
algotrading
nextjs
open-source
stock-api
trading-bot-monitoring
typescript

README

open-trade-bot — a free Next.js trading-bot starter

open-trade-bot

A free, open-source Next.js starter for a stock trading bot — wired to a signals API, running itself on a daily cron. Ships in paper-trading mode.

License: MIT Next.js TypeScript Paper trading

Deploy with Vercel


Most "build a trading bot" tutorials either hand-wave the strategy ("insert your alpha here") or bury you in backtesting before you've written a line. This does the opposite: it treats the strategy as an external input (the Picckles Signals API, a read-only REST endpoint of daily buy/sell signals) and focuses on the engineering that actually trips people up — scheduling, persistence, idempotency, and deploy.

It ships in paper-trading mode so you can watch it work with zero broker setup. Going live is one function to swap (runTick in src/lib/bot.ts).

Architecture

Vercel Cron  (weekdays, 21:05 UTC — just after the US close)
      │
      ▼
GET /api/run ──► runTick(strategy)
                     │
                     ├─► picckles.ts   fetch SELL/HOLD on held positions, then today's BUY signals
                     ├─► bot.ts        resolve exits, size new entries to budget, skip symbols already held
                     └─► store.ts      persist positions + trade ledger to Upstash Redis
      ▲
      │
 Dashboard  ( / )  ──►  "Run now" button triggers a manual tick

What it does

Each tick (GET /api/run, hit by Vercel Cron or your own scheduler):

  1. Asks the API for SELL / HOLD decisions on any position it's currently holding, and paper-sells the SELLs.
  2. Asks the API for today's BUY signals, sizes them to your per-trade budget, and paper-buys anything new (skipping symbols it already owns). A crash gate can suppress new entries on high-VIX days.
  3. Persists positions and a trade ledger to Upstash Redis.

The dashboard (/) shows open positions and recent trades, with a Run now button to fire a tick manually — handy for trying it out without waiting for the cron.

How it's laid out

FileRole
src/app/api/run/route.tsThe cron/HTTP entry point — one tick per request
src/lib/bot.tsrunTick() — the whole trading loop (exits → entries → persist)
src/lib/picckles.tsThin fetch client for the signals API
src/lib/store.tsUpstash Redis: positions + trade ledger
src/app/page.tsx + RunButton.tsxThe dashboard and manual-run button
vercel.jsonThe daily cron schedule

Quickstart

git clone https://github.com/rkang30/open-trade-bot
cd open-trade-bot
npm install

cp .env.example .env.local
# - free API key:     https://picckles.com/api-pricing
# - free Upstash Redis (so positions persist): https://upstash.com

npm run dev

Open localhost:3000 and click Run now.

Deploying

  1. Push to GitHub, import into Vercel (or use the Deploy with Vercel button above).
  2. Add the env vars from .env.example (PICCKLES_API_KEY, UPSTASH_REDIS_REST_URL / _TOKEN, a random CRON_SECRET).
  3. vercel.json already schedules /api/run for 5 21 * * 1-5 (21:05 UTC, weekdays — shortly after the US close). Adjust to taste.

Strategies

Set STRATEGY in your env to either:

StrategyStyleTypical hold
double7-guarded (default)Buy a strong uptrend on a short-term low, with a VIX crash gate~2–3 weeks
rs-pullbackBuy a relative-strength leader on a fast capitulation dip~2–5 days

Full entry/exit rules: picckles.com/api-docs#strategies.

Going live

Everything routes through runTick() in src/lib/bot.ts, which currently only records paper trades via logTrade(). Add a real broker call (Alpaca, Interactive Brokers, etc.) alongside it and the rest of the bot — signal fetching, exit checks, position tracking — is unchanged. The signals client is a plain fetch, so pointing it at a different endpoint is a small edit too.

FAQ

Is it free? The code is MIT. The signals API and Upstash Redis both have free tiers, so you can run the whole thing at $0.

Do I need to know a trading strategy? No — that's the point. The API supplies the entry/exit decisions; this repo is the runnable wiring around them.

Does it place real trades? No. It's paper-trading by default — no broker keys, no real orders. Wiring a real broker is opt-in and on you (see Going live).

Can I use a different signals source or broker? Yes. src/lib/picckles.ts is a thin fetch client and runTick() is broker-agnostic — swap either without touching the core loop.

How does it avoid double-buying if a cron tick retries? Before buying, runTick() loads current positions from Redis and skips any symbol it already holds, and signals only change once per trading day — so re-running a tick (cron retry or the manual button) won't double-buy.

Why Redis instead of a database? Serverless functions are stateless; positions need to survive between invocations. Redis is the smallest thing that does that. Swap src/lib/store.ts for Postgres if you'd rather.

Learn how it's built

Step-by-step tutorial with the reasoning behind each piece: How to Build a Stock Trading Bot with Next.js and a Trading Signals API

Disclaimer

Signals are informational only and identical for every API subscriber — not personalized investment advice. This bot trades paper money by default; you are responsible for anything you connect to a real broker. Past performance does not predict future results.

License

MIT

Contributors

rkang30

4 commits

Languages

TypeScript

93.5%

JavaScript

3.5%

CSS

3.0%