1 line
18 KiB
JSON
1 line
18 KiB
JSON
{"repo": "bdmisme/us-stock-radar", "files": {"README.en.md": {"098b00294a3d526e5f7d468c7bd7152504d30b68": {"t": 1785674252.621466, "n": 8839, "h": "f64f3a59338593a6", "c": "# 📡 us-stock-radar\n\n> **Language**: English ↔ [繁體中文](README.md)\n\nA personal **US-stock AI monitoring radar**. It watches your **holdings / high-focus / general watchlist**, computes technical indicators, detects abnormal events with a rules engine, and a resident **AI analyst** (any OpenAI-compatible LLM) proactively produces **structured research and risk reminders** — with Email / Telegram alerts on major events. The UI uses the **Taiwan color convention (🔴 up / 🟢 down)**.\n\n> ⚠️ **Disclaimer**: This tool is for **personal monitoring and investment research only**.\n> It **never places orders, never connects to any broker trading API, and never guarantees profit**. AI output is research and risk commentary, **not investment advice**. You are responsible for your own decisions.\n\n<p align=\"center\">\n <img src=\"docs/img/portfolio.png\" width=\"80%\" alt=\"Portfolio: heatmap + groups + P&L\" />\n</p>\n\n---\n\n## 🖼️ Screenshots\n\n| Portfolio (heatmap + groups + P&L) | Candlestick (drag-to-pan / scroll-zoom / range buttons) |\n| :---: | :---: |\n|  |  |\n| **Watchlist (buy-zone highlights)** | **AI Analyst (structured research)** |\n|  |  |\n\n---\n\n## ✨ Features\n\n| Module | What it does |\n| --- | --- |\n| Real-time quotes | **Alpaca IEX WebSocket** for live trades (holdings + high-focus, capped at 30), auto-reconnect |\n| History / after-hours | Alpaca historical REST as primary (cloud-reliable); a startup `backfill` seeds daily bars + indicators so you see **the prior close even when the market is closed** |\n| Fallback polling | General watchlist polled via Finnhub → FMP → yfinance chain (rate-limited) |\n| Indicators | MA5/10/20/60/120, RSI14, MACD, Bollinger, VWAP, volume ratio, distance-to-MA% |\n| Signal Engine | 15 rule-based events (MA break/reclaim, RSI extremes, MACD cross, volume spike, % moves, near stop/target, cost breakout…) |\n| AI Analyst | Resident worker reads the event queue and calls the LLM for structured JSON; tiered **cooldown** (swing 2h / long-term & high-focus 4h) to cut noise |\n| Scheduling | Tiered analysis cadence (pre-open / intraday / close, US-Eastern session) |\n| Holdings mgmt | **Long-term / swing** classification, **custom groups**, stop/target, bulk management |\n| Watchlist | High-focus / general, **buy-zone status** (in-zone / below / above target), theme tags |\n| News | Finnhub / FMP / RSS fetch + AI summary & bullish/bearish read |\n| Alerts | Telegram Bot + Email SMTP (gracefully marked `skipped` if unconfigured) |\n| Dashboard | Streamlit, 7 pages: Overview / Portfolio / Watchlist / Signals / AI Analyst / News / Settings |\n\n**Core design: the rules engine compresses raw ticks into events before the LLM sees anything** — the LLM never reads per-second ticks, saving tokens and noise. Resident processes coordinate purely through SQLite (WAL mode) `signals` / `alerts` status columns as an event queue — **no Redis / Kafka needed**.\n\n---\n\n## 🏗️ Architecture\n\n```mermaid\nflowchart LR\n subgraph sources[\"Data sources (data_adapters/)\"]\n AL[\"Alpaca IEX WS<br/>+ historical REST\"]\n FB[\"Finnhub / FMP / yfinance<br/>(fallback polling)\"]\n end\n MM[\"market_monitor\"]\n TI[\"indicators/technical\"]\n SE[\"signal_engine<br/>15 rule events\"]\n DB[(\"SQLite (WAL)<br/>signals / alerts<br/>= event queue\")]\n AW[\"ai_worker<br/>→ Any OpenAI-compatible LLM\"]\n ALW[\"alert_worker<br/>Telegram / Email\"]\n UI[\"Streamlit Dashboard<br/>7 pages\"]\n\n AL --> MM\n FB --> MM\n MM --> DB\n DB --> TI --> DB\n DB --> SE -->|critical → pending_ai| DB\n DB -->|poll pending_ai| AW -->|structured analysis| DB\n DB -->|high risk| ALW\n DB --> UI\n```\n\n> Upgrading to a paid full-market SIP feed is just one new adapter (implementing the `data_adapters/base.py` interface) swapped into `market_monitor` — nothing downstream changes. See bottom.\n\n---\n\n## 🚀 Quickstart\n\n> ⚠️ **Every API key is optional.** Missing keys cause **graceful degradation** (fallback or `skipped`), never a crash. The more you fill in, the more complete it gets.\n\n### A. Local (venv)\n\n```bash\ngit clone https://github.com/BDMisME/us-stock-radar.git\ncd us-stock-radar\n\n# macOS system python3 is usually too old (3.9); use 3.11+ (brew 3.12 recommended)\npython3.12 -m venv .venv\nsource .venv/bin/activate\npip install -r requirements.txt\n\ncp .env.example .env # fill in your own keys (all blank still runs the demo)\n\npython scripts/init_db.py # create tables\npython scripts/seed_demo.py # demo: 20 holdings + 80 watchlist\npython scripts/backfill.py # seed daily bars + indicators (instant data)\n\nstreamlit run app/main.py # → http://localhost:8501\n```\n\nFor live monitoring / AI / alerts, run the resident services (one terminal each):\n\n```bash\npython services/market_monitor.py\npython services/signal_engine.py\npython services/ai_worker.py\npython services/alert_worker.py\npython services/scheduler.py\n```\n\n### B. Docker (everything in one command)\n\n```bash\ncp .env.example .env\ndocker compose up --build # Dashboard → http://localhost:8501\n```\n\n### C. Zeabur (cloud)\n\n1. Fork this repo, connect it to Zeabur.\n2. Set the env vars (same as `.env`); **mount a Persistent Volume at `/data`** and set `DB_PATH=/data/us_stock_radar.sqlite`.\n3. `start.sh` auto-runs init → seed → backfill → all services + dashboard.\n\n---\n\n## 🔑 Getting API keys (all optional)\n\n| Service | Used for | Free tier | Sign up |\n| --- | --- | --- | --- |\n| **Alpaca** | Live quotes + historical bars (**start here**) | Free IEX real-time + history | <https://alpaca.markets/> |\n| **Any OpenAI-compatible LLM** | AI analyst | Varies by provider — see note below | — |\n| **Finnhub** | Fallback quotes / news | Free tier | <https://finnhub.io/> |\n| **FMP** | Fallback quotes / fundamentals | Free tier | <https://site.financialmodelingprep.com/> |\n| **Telegram Bot** | Major-event push | Free | Get a bot token from [@BotFather](https://t.me/BotFather) |\n\n> **LLM setup**: set `LLM_API_KEY` / `LLM_BASE_URL` / `LLM_MODEL` in `.env`. Common choices:\n> - **OpenAI**: `LLM_MODEL=gpt-4o`, leave `LLM_BASE_URL` blank\n> - **Groq** (free tier): `LLM_BASE_URL=https://api.groq.com/openai/v1`, `LLM_MODEL=llama-3.3-70b-versatile`\n> - **Volcengine ARK**: `LLM_BASE_URL=https://ark.cn-beijing.volces.com/api/v3`, `LLM_MODEL=<endpoint-id>`\n> - **Gemini** (OpenAI-compat): `LLM_BASE_URL=https://generativelanguage.googleapis.com/v1beta/openai/`, `LLM_MODEL=gemini-2.0-flash`\n\n> Just want to see the UI? **Leave everything blank** — demo data + backfill render the full dashboard.\n\n---\n\n## ❓ FAQ\n\n- **No live quotes after hours / on weekends?** It backfills the **prior close** from Alpaca history, so the UI is never blank.\n- **Do I need a paid data feed?** No. Free Alpaca IEX + history is enough for personal use; upgrade to SIP only if you want full-market real-time.\n- **Why is red = up and green = down?** It follows the **Taiwan convention** (🔴 up / 🟢 down), opposite of the US. Charts and tables are consistent.\n- **Will the AI trade for me?** **No, and it never will.** There is zero order/trading API in this project — research and risk reminders only.\n\n---\n\n## 🔒 Security & Privacy\n\n- **Keys live only in `.env`** (gitignored, never committed); this repo contains no real secrets.\n- Self-hosting? Use **your own** keys; the sidebar credit is customizable via the `APP_CREDIT_NAME` env var.\n- ⚠️ **This is single-user by design — there is no login / auth.** If you deploy it to a public URL, anyone can view and edit your settings — **don't share your live instance URL publicly; share this repo instead.**\n\n---\n\n## 🧪 Tests\n\n```bash\npytest # indicators, signal-engine rules, DB/queue, AI JSON parsing (mocked LLM)\n```\n\n---\n\n## 🔌 Upgrading the data source (future)\n\nEvery quote source implements the `data_adapters/base.py` interface:\n\n```python\nclass QuoteAdapter: # get_quote(symbol) / get_quotes(symbols)\nclass HistoryAdapter: # get_bars(symbol, timeframe, limit)\nclass NewsAdapter: # get_news(symbol, limit)\n```\n\nAdd one adapter, swap it into `market_monitor`, and nothing downstream (indicators / signal engine / AI / dashboard) changes:\n\n- **Alpaca SIP** — switch `DataFeed.IEX` to `DataFeed.SIP` (subscription) for full-market real-time.\n- **dxFeed Nasdaq Basic** — add `data_adapters/dxfeed_stream.py` implementing `QuoteAdapter`.\n- **Finazon SIP** — add `data_adapters/finazon_client.py` implementing `QuoteAdapter` + `HistoryAdapter`.\n\n---\n\n## 🤝 Contributing\n\nIssues and PRs welcome. Please run `pytest` (green) first. See [CONTRIBUTING.md](CONTRIBUTING.md).\n\n## 📄 License\n\n[MIT](LICENSE) © 2026 BDMisME\n\n> Credit to reference projects (read-only, no code merged): tradingagents, stocks-analysis-ai-agents, ai-stock-dashboard, streamlit-stock-analysis.\n"}}, "README.md": {"098b00294a3d526e5f7d468c7bd7152504d30b68": {"t": 1785674280.790249, "n": 5977, "h": "540e5580ee748f11", "c": "# 📡 us-stock-radar\n\n> **語言**:繁體中文 ↔ [English](README.en.md)\n\n個人用「美股 AI 看盤雷達」。監控**持股 / 高關注 / 一般觀察名單**,自算技術指標、用規則引擎偵測異常事件,由常駐 AI 分析師(**任何 OpenAI 相容 LLM**)主動產生**結構化研究與風險提醒**,並透過 Email / Telegram 通知重大事件。介面採**台股慣例配色(🔴 漲 / 🟢 跌)**。\n\n> ⚠️ **重要聲明**:本工具僅供**個人監控與投資研究**。\n> **不自動下單、不串接任何券商交易 API、不保證獲利**,AI 內容僅為研究與風險提醒,**非投資建議**。請自行判斷並承擔投資決策。\n\n<p align=\"center\">\n <img src=\"docs/img/portfolio.png\" width=\"80%\" alt=\"持股總覽:熱力圖 + 分組 + 損益表\" />\n</p>\n\n---\n\n## 🖼️ 畫面預覽\n\n| 持股(熱力圖 + 分組 + 損益) | 個股 K 線(拖曳平移 / 滾輪縮放 / 時間快捷鈕) |\n| :---: | :---: |\n|  |  |\n| **觀察名單(買區狀態高亮)** | **AI 分析師(結構化研究)** |\n|  |  |\n\n---\n\n## ✨ 功能總覽\n\n| 模組 | 說明 |\n| --- | --- |\n| 即時行情 | **Alpaca IEX WebSocket** 訂閱即時報價(持股+高關注,上限 30 檔),斷線自動重連 |\n| 歷史 / 盤後 | Alpaca 歷史 REST 為主(雲端可靠);開機 `backfill` 先補日 K+指標,**休市也看得到前一日收盤** |\n| 備援輪詢 | 一般觀察名單以 Finnhub → FMP → yfinance 鏈式輪詢(含 rate limit) |\n| 技術指標 | MA5/10/20/60/120、RSI14、MACD、Bollinger、VWAP、量比、距均線% |\n| Signal Engine | 15 種規則事件(跌破/站上 MA、RSI 超買超賣、MACD 交叉、放量、漲跌幅、接近停損停利、突破成本…)|\n| AI 分析師 | 常駐讀取事件 queue,呼叫 LLM 產生結構化 JSON;分層**冷卻**(短線 2h / 長期・高關注 4h)避免雜訊 |\n| 排程分析 | 開盤前 / 盤中 / 收盤的分層分析頻率(美東時段) |\n| 持股管理 | **長期 / 短線**分類、**自訂群組**、停損停利、批次管理 |\n| 觀察名單 | 高關注 / 一般觀察、**買區狀態**(在買區 / 低於 / 高於目標)、主題標籤 |\n| 新聞 | Finnhub / FMP / RSS 抓取 + AI 摘要與利多利空判斷 |\n| 通知 | Telegram Bot + Email SMTP(未設定則自動標記 skipped,不崩潰) |\n| Dashboard | Streamlit 7 頁:總覽 / 持股 / 觀察名單 / 訊號 / AI 分析師 / 新聞 / 設定 |\n\n**設計核心:規則引擎先把 raw tick 壓縮成事件,再交給 LLM 分析** —— LLM 絕不直接讀每秒報價,省 token、降雜訊。各常駐 process 透過 SQLite(WAL 模式)的 `signals` / `alerts` 狀態欄當作 event queue 溝通,**無需 Redis / Kafka**。\n\n---\n\n## 🏗️ 架構\n\n```mermaid\nflowchart LR\n subgraph sources[\"資料源 (data_adapters/)\"]\n AL[\"Alpaca IEX WS<br/>+ 歷史 REST\"]\n FB[\"Finnhub / FMP / yfinance<br/>(備援輪詢)\"]\n end\n MM[\"market_monitor<br/>行情擷取\"]\n TI[\"indicators/technical<br/>技術指標\"]\n SE[\"signal_engine<br/>15 種規則事件\"]\n DB[(\"SQLite (WAL)<br/>signals / alerts<br/>= event queue\")]\n AW[\"ai_worker<br/>→ 任何 OpenAI 相容 LLM\"]\n ALW[\"alert_worker<br/>Telegram / Email\"]\n UI[\"Streamlit Dashboard<br/>7 頁\"]\n\n AL --> MM\n FB --> MM\n MM --> DB\n DB --> TI --> DB\n DB --> SE -->|重大事件 pending_ai| DB\n DB -->|撈 pending_ai| AW -->|結構化分析| DB\n DB -->|高風險| ALW\n DB --> UI\n```\n\n> 升級到付費全市場 SIP 資料只需新增一個 adapter(實作 `data_adapters/base.py` 介面)並在 `market_monitor` 換接,下游完全不用改。詳見文末。\n\n---\n\n## 🚀 Quickstart\n\n> ⚠️ **所有 API key 皆為選填**。缺 key 時各模組會**優雅降級**(fallback 或標記 skipped),不會崩潰;填越多功能越完整。\n\n### A. 本地(venv)\n\n```bash\ngit clone https://github.com/BDMisME/us-stock-radar.git\ncd us-stock-radar\n\n# macOS 內建 python3 多半過舊(3.9),請用 3.11+(建議 brew 的 3.12)\npython3.12 -m venv .venv\nsource .venv/bin/activate\npip install -r requirements.txt\n\ncp .env.example .env # 填入你自己的 key(全部留空也能跑 demo)\n\npython scripts/init_db.py # 建表\npython scripts/seed_demo.py # 載入 demo:20 持股 + 80 觀察名單\npython scripts/backfill.py # 補日 K + 指標(讓畫面立刻有資料)\n\nstreamlit run app/main.py # → http://localhost:8501\n```\n\n要啟用即時監控 / AI / 通知,再各開一個終端機跑常駐服務:\n\n```bash\npython services/market_monitor.py # 行情擷取(WebSocket + 輪詢)\npython services/signal_engine.py # 異常事件偵測\npython services/ai_worker.py # AI 分析師\npython services/alert_worker.py # 通知派送\npython services/scheduler.py # 分層排程分析\n```\n\n### B. Docker(一鍵啟動全部)\n\n```bash\ncp .env.example .env # 填好 key\ndocker compose up --build # Dashboard → http://localhost:8501\n```\n\n### C. Zeabur(雲端部署)\n\n1. Fork 本 repo,連到 Zeabur。\n2. 在 Zeabur 後台填入環境變數(同 `.env`);**掛載 Persistent Volume 到 `/data`** 並設 `DB_PATH=/data/us_stock_radar.sqlite`。\n3. `start.sh` 會自動建表、seed、backfill、啟動所有服務與 Dashboard。\n\n---\n\n## 🔑 如何取得 API Key(全部選填)\n\n| 服務 | 用途 | 免費額度 | 申請連結 |\n| --- | --- | --- | --- |\n| **Alpaca** | 即時報價 + 歷史 K(**最推薦先辦這個**) | 免費 IEX 即時 + 歷史資料 | <https://alpaca.markets/> |\n| **任意 OpenAI 相容 LLM** | AI 分析師 | 各家不同,見下方說明 | — |\n| **Finnhub** | 備援報價 / 新聞 | 免費 tier | <https://finnhub.io/> |\n| **FMP** | 備援報價 / 基本面 | 免費 tier | <https://site.financialmodelingprep.com/> |\n| **Telegram Bot** | 重大事件推播 | 免費 | 跟 [@BotFather](https://t.me/BotFather) 申請 bot token |\n\n> **LLM 設定方式**:在 `.env` 填入 `LLM_API_KEY` / `LLM_BASE_URL` / `LLM_MODEL`。常見選擇:\n> - **OpenAI**:`LLM_MODEL=gpt-4o`,`LLM_BASE_URL` 留空\n> - **Groq**(免費額度):`LLM_BASE_URL=https://api.groq.com/openai/v1`,`LLM_MODEL=llama-3.3-70b-versatile`\n> - **火山方舟 ARK**:`LLM_BASE_URL=https://ark.cn-beijing.volces.com/api/v3`,`LLM_MODEL=<endpoint-id>`\n> - **Gemini**:`LLM_BASE_URL=https://generativelanguage.googleapis.com/v1beta/openai/`,`LLM_MODEL=gemini-2.0-flash`\n\n> 只想先看畫面?**全部留空**直接跑,demo 資料 + backfill 就能看到完整 UI。\n\n---\n\n## ❓ FAQ\n\n- **盤後 / 假日沒有即時報價怎麼辦?** 系統會用 Alpaca 歷史資料補上**前一日收盤**,畫面不會空白。\n- **一定要付費資料源嗎?** 不用。免費 Alpaca IEX + 歷史就足夠個人使用;要全市場即時再升級 SIP。\n- **為什麼紅色是漲、綠色是跌?** 採**台股慣例**(🔴 漲 / 🟢 跌),與美股相反。圖表與表格一致。\n- **AI 會幫我下單嗎?** **不會,也永遠不會。** 本專案無任何下單 / 交易 API,僅做研究與風險提醒。\n\n---\n\n## 🔒 安全與隱私\n\n- **金鑰只放 `.env`**(已被 `.gitignore` 排除,永不進 git);本 repo 不含任何真實金鑰。\n- 自架請填入**你自己的** key;側欄署名可用 `APP_CREDIT_NAME` 環境變數自訂。\n- ⚠️ **本工具為單用戶設計,沒有登入 / 權限機制**。若你把實例部署到公開網址,任何人都能看到並修改你的設定 —— **請勿公開分享你的線上實例網址,要分享請分享本 repo**。\n\n---\n\n## 🧪 測試\n\n```bash\npytest # 涵蓋技術指標、Signal Engine 規則、DB/queue、AI JSON 解析(mock LLM)\n```\n\n---\n\n## 🔌 升級資料源(未來)\n\n所有行情來源都實作 `data_adapters/base.py` 介面:\n\n```python\nclass QuoteAdapter: # get_quote(symbol) / get_quotes(symbols)\nclass HistoryAdapter: # get_bars(symbol, timeframe, limit)\nclass NewsAdapter: # get_news(symbol, limit)\n```\n\n新增一個 adapter 並在 `market_monitor` 換接即可,下游(指標 / Signal Engine / AI / Dashboard)完全不需改:\n\n- **Alpaca SIP** — 把 `DataFeed.IEX` 換成 `DataFeed.SIP`(需訂閱),即得全市場即時。\n- **dxFeed Nasdaq Basic** — 新增 `data_adapters/dxfeed_stream.py` 實作 `QuoteAdapter`。\n- **Finazon SIP** — 新增 `data_adapters/finazon_client.py` 實作 `QuoteAdapter` + `HistoryAdapter`。\n\n---\n\n## 🤝 貢獻\n\n歡迎 issue / PR。請先跑 `pytest` 確認綠燈。詳見 [CONTRIBUTING.md](CONTRIBUTING.md)。\n\n## 📄 授權\n\n[MIT](LICENSE) © 2026 BDMisME\n\n> 致謝參考專案(僅閱讀、未合併程式碼):tradingagents、stocks-analysis-ai-agents、ai-stock-dashboard、streamlit-stock-analysis。\n"}}}} |