Oracle3
Oracle3: 예측시장 거래 엔진·MCP 서버
기관 수준 AI 시장 분석으로 주문 흐름·유동성·시장 구조·청산·확률적 매매 설정과 투명한 근거 제공
Institutional-grade AI market analysis: order flow, liquidity, market structure, liquidations and probabilistic trade setups with transparent reasoning.
금융TypeScript · CSSGitHub @Hamzaabidbutt온라인운영자 미확인
써 보셨어요? 한 번만 눌러 주세요. 로그인은 필요 없어요.
아직 감지된 업데이트가 없습니다. GitHub 릴리스가 나오면 여기에 보입니다.
개인 계정의 공개 저장소 소유자는 GitHub로 로그인해 운영자를 확인하고 소개를 직접 관리할 수 있습니다. 관리자 승인은 필요하지 않습니다.
로그인한 뒤 확인 파일을 만들어 이 저장소의 기본 브랜치에 30분 안에 커밋해 주세요. 다른 브랜치나 포크의 파일은 인정하지 않습니다. 파일을 올린 뒤 아래에서 확인하면 관리자 승인 없이 관리할 수 있습니다. 자격을 유지하려면 파일을 남겨 두세요.
로그인이 필요하면 로그인 화면으로 이동합니다. 로그인 후 이곳으로 돌아와 원하는 확인 버튼을 다시 눌러 주세요.
프로젝트 폴더에서 /nomorevibe verify를 실행하면 소유권을 확인하고 소개를 직접 관리할 수 있습니다.
1분 만에 확인하기README 전체를 불러오는 중입니다. 아래는 저장된 발췌입니다.
AI-powered, institutional-style crypto market intelligence & signal platform.
TradingMaster continuously analyzes live futures market data — order flow, liquidity, market
structure, volume behavior, liquidations and price action — to estimate the highest-probability
next move, then generates complete trade setups (entry / stop / TP1-3 / RR / confidence) with the
full evidence stack behind every call. It is not an indicator site: every signal explains why
it exists.
Built with Next.js 14 (App Router) + TypeScript + MySQL (Prisma) + Tailwind + lightweight-charts.README 전문 보기 ↗AI-powered, institutional-style crypto market intelligence & signal platform.
TradingMaster continuously analyzes live futures market data — order flow, liquidity, market structure, volume behavior, liquidations and price action — to estimate the highest-probability next move, then generates complete trade setups (entry / stop / TP1-3 / RR / confidence) with the full evidence stack behind every call. It is not an indicator site: every signal explains why it exists.
Built with Next.js 14 (App Router) + TypeScript + MySQL (Prisma) + Tailwind + lightweight-charts.
| Area | What it does |
|---|---|
| Markets | UNI, ORDI, BTC, ETH, SOL, BNB, DEXE vs USDT (Binance USDT-M futures). Add a row to src/lib/config.ts → the entire platform picks it up. |
| Timeframes | 1m → 1M, each with independent structure & analysis. |
| Chart | TradingView-style candles with live websocket updates plus auto-drawn overlays, all individually toggleable from the Indicators panel: order blocks (fresh/respected/mitigated), breaker blocks, FVGs (+fill state), supply/demand, premium/discount + equilibrium, BOS/CHOCH markers, liquidity sweeps, equal highs/lows connected with lines, buy/sell-side liquidity, S/R, volume profile histogram with POC/VAH/VAL/LVN lines, auto Fibonacci with golden pocket, key moving averages (EMA 9/21/50, SMA 100/200), session VWAP, CVD line, big-trade bubbles, absorption/exhaustion/trap markers, entry/SL/TP levels, pattern markers. |
| Numeric rows | Printed under the price panel and toggleable: volume numbers, volume delta numbers (green/red by sign), aggregate liquidation delta per bar, and a buy-pressure ribbon shaded by how far each bar leans from neutral. A cumulative aggregate liquidation delta line (running forced-flow balance) is available as its own pane. Numbers auto-thin as you zoom out so they never overlap. |
| Volume Profile & Auction Theory | POC (Point of Control), 70% Value Area with VAH/VAL, HVN (accepted price) and LVN (rejected price — the better trade location) detection, profile shape classification (D balanced, P short covering, b long liquidation, B double distribution) and balance ↔ imbalance auction state with value acceptance above/inside/below. |
| Footprint | Per-price bid × ask ladder rebuilt from lower-timeframe candles (fidelity is reported: reconstructed vs modelled), diagonal imbalance detection at a configurable 3x threshold, stacked imbalances (3+ consecutive levels), zero prints, per-candle POC, and delta-vs-body divergence — the classic absorption/trap signature. |
| Absorption / Exhaustion / Traps | Absorption scored only where it matters — at the POC, value-area edges, LVNs or strong S/R (mid-range absorption is explicitly down-weighted as noise). Exhaustion tracked in three stages (momentum → weakening → danger) including the hollow low-volume push into a new extreme. Trapped buyers/sellers identified with the stop pool they left behind. |
| Delta & CVD | Per-bar delta, cumulative volume delta, regular and hidden CVD divergences (earlier than any price-derived oscillator), trap bars where delta contradicts the candle body, and delta-spike levels that act as future S/R. |
| Market structure engine | Fractal swings (major/minor), HH/HL/LH/LL labeling, BOS & CHOCH detection on both structure scopes, range detection, trend + reversal/continuation probabilities. |
| Order flow engine | Buy/sell pressure, per-bar delta, cumulative delta (CVD), aggression, absorption, exhaustion, large-order detection — derived from taker-buy volume. |
| Liquidity engine | Equal highs/lows clustering, swing liquidity pools, buy/sell stops, sweep/grab/hunt detection with reversal vs continuation odds and plain-language explanation of who likely drove it. |
| Liquidation engine | Heuristic cascade detection from price/volume/delta signatures, long/short pressure, cluster heat map projection, whale-driven & fake-move classification, plus the live forced-order tape streamed from Binance (@forceOrder). |
| Patterns | Engulfing, hammer, shooting star, morning/evening star, doji, inside/outside bar, pin bars, marubozu, strong rejection candles — each with top/bottom price, strength, contextual probability. Double/triple tops & bottoms with neckline, measured target and breakout odds. |
| S/R engine | Clustered levels with strength (0-100), touch & rejection counts, break/bounce probabilities, volume confirmation. |
| Market Pulse (5-min conclusion) | A tab inside the signal panel that answers "what just happened and what's next": explicit bullish/bearish odds with a transparent factor breakdown, the most traded prices in the window, the institutional footprint band (classified accumulation / distribution / neutral), bearish candles that closed with positive delta (and the bullish mirror) as absorbed-aggression tells, stop hunts, large prints, window vitals and a projected target with its invalidation level. Runs on 1-minute candles regardless of chart timeframe. |
| Live candles | The in-progress candle updates on every websocket frame, closed bars fold into state the instant they finish, and refetches reconcile incrementally so panning/zooming is never reset. A countdown to candle close sits beside the price axis, TradingView-style, alongside the live price. |
| Multi-Window Read | The same tape analysed across 3, 5, 7, 10, 12 and 15-bar lookbacks side by side, each with its own odds, delta, buy%, POC, volume multiple and close position. Reports the consensus (how many horizons agree) and flags divergence when short lookbacks turn against long ones — an early reversal tell no single lookback can produce. |
| AI analyst panel | Continuously updating desk-analyst feed ("Buyers absorbing aggressive sellers", "Short liquidations increasing", "Distribution phase detected"…), every line backed by the evidence that produced it. |
| Signal engine | 28 strategies vote -100..+100 — smart-money (SMC, ICT, liquidity sweep, order block, FVG, CHOCH, BOS), price action (breakout, trend continuation, reversal, engulfing, S/R, Fibonacci, MA stack) and order flow (key-level absorption, exhaustion reversal, trapped traders, CVD divergence, stacked imbalance, value area/auction, LVN rejection, VWAP, liquidation delta, equal-level liquidity). A tanh-squashed weighted blend produces bullish/bearish probability and a Weak/Moderate/Strong/Very Strong confidence label. Setups ladder TPs into resting liquidity, stop beyond structural invalidation, and always include reasoning + invalidation conditions. |
| Backtesting | Walk-forward, no lookahead, pessimistic intrabar resolution. Win rate, profit factor, max DD, Sharpe, streaks, avg RR, monthly/yearly buckets, equity curve; per-strategy isolation and comparison. |
| Learning engine | Every closed signal produces an immutable LearningRecord; strategy weights adjust (bounded, small learning rate) toward strategies that were right. History is never deleted. |
| Analytics | Real measured win rates (today/week/month/all-time), per-strategy accuracy, best/worst strategy — never a hardcoded accuracy claim. |
| Alerts | Browser notifications, Telegram, Discord, generic webhooks (env-configured) + per-user webhook channels. Liquidation-spike alerts push forced flow printing at an extreme straight to your phone — gated, deduplicated per spike and rate-limited per symbol (see below). |
| Security | JWT httpOnly sessions, bcrypt, RBAC (ADMIN/ANALYST/VIEWER), zod input validation, per-IP rate limiting (middleware + per-route), audit log, security headers. |
src/
engines/ Pure, deterministic analysis engines (no I/O — unit-testable)
marketStructure, orderBlocks, fvg, liquidity, candlestick,
supportResistance, volume, orderflow, liquidations, doublePatterns,
premiumDiscount, volumeProfile, footprint, orderFlowEvents,
deltaAnalysis, liquidationDelta, indicators (MA/VWAP/Fib/equal levels),
strategies, signal, insights, analyzer, backtest, learning
services/ Signal lifecycle: generate → persist → evaluate → learn
lib/ Binance client, Prisma, auth, cache, rate limit, logger, alerts, config
app/ Next.js App Router pages + REST API routes
components/ Chart (lightweight-charts + custom overlay canvas), panels, shell
hooks/ Live websocket market feed, analysis polling
stores/ Zustand UI state (persisted)
scripts/worker.ts Background scanner: analyzes all markets, persists signals,
evaluates open trades, feeds the learning engine
prisma/ MySQL schema + seed
tests/ Vitest unit/integration tests for the engines
Data flow: Binance REST (klines/ticker/depth) → analysis engines → API/worker → MySQL.
Browser additionally connects straight to Binance websockets (kline, markPrice, forceOrder)
for zero-latency chart ticks and the live liquidation tape.
cp .env.example .env # set AUTH_SECRET at minimum
docker compose up --build
# → web on http://localhost:3000, MySQL, migrations+seed, background worker
cp .env.example .env # point DATABASE_URL at your MySQL, set AUTH_SECRET
npm install # runs prisma generate
npx prisma db push && npm run db:seed
npm run dev # web → http://localhost:3000
npm run worker # background signal scanner (separate terminal)
npm test # engine test suite
The dashboard works without a database (analysis is computed live); MySQL enables signal persistence, learning, analytics and auth. The first registered account becomes ADMIN.
Binance geo-blocking (important for cloud deploys). Binance returns HTTP 451 to a number of datacentre regions, notably US ones. Vercel's default function region is
iad1(US East), so a default deploy will show an empty chart and a stuck "Connecting to market feed…" strip while the browser's own websocket connects fine.This repo ships a
vercel.jsonpinning functions tofra1(Frankfurt). Other permitted regions includesin1,hnd1andsyd1. On other hosts, deploy outside the US or pointBINANCE_FAPI_BASEat a reachable mirror/proxy.As a safety net the UI falls back to fetching klines and tickers directly from the visitor's browser when the server route fails, and shows a banner saying so. That keeps the chart alive, but the server-side analysis panels still require a server that can reach Binance.
Forced flow is price-insensitive — a margin engine closes because collateral ran out, not because it has a view — so it is finite by construction. When it lands at the extreme of a move and price holds, the pressure that made the extreme has been spent. These alerts fire on exactly that: a spike at an extreme, with a forced signature, that has already begun reversing.
# 1. Create a bot with @BotFather in Telegram, then message your new bot once.
# 2. Find your chat id — this script says WHY it is missing when it is:
# npm run telegram:chat-id -- <token>
# npm run telegram:chat-id -- --test <chat-id> # prove it end to end
# (Shortcut for a DM: message @userinfobot. The id it reports is your own
# user id, which is the chat id for a private chat with your bot.)
TELEGRAM_BOT_TOKEN="123456:ABC..."
TELEGRAM_CHAT_ID="987654321"
# 3. Secret for the scheduled endpoint. Without it the route stays disabled.
CRON_SECRET="$(openssl rand -base64 32)"
APP_URL="https://your-app.vercel.app" # used for the link inside each alert
Then apply the schema (SentAlert is new) and check the gate before pointing it at a live channel:
npm run db:push
curl "$APP_URL/api/alerts/liquidations?dry=1&secret=$CRON_SECRET"
dry=1 evaluates and reports without sending or recording anything.
Something has to call the endpoint; the app is serverless and nothing runs between page loads.
| Option | Granularity | Notes |
|---|---|---|
| GitHub Actions (shipped) | 5 min | Free, works on a Vercel Hobby plan, secret stays in repo secrets. See below. |
npm run worker | LIQ_ALERT_INTERVAL_SEC (default 300s) | Best latency, but needs an always-on host (Railway/Fly/Render/VPS). |
| Vercel Cron | 1 min on Pro, once a day on Hobby | Add a crons entry to vercel.json; Vercel sends CRON_SECRET as a bearer token automatically. |
| cron-job.org / Upstash QStash | 1 min | Free tiers. Send the secret as a header, not in the URL — query strings land in access logs. |
.github/workflows/liquidation-alerts.yml calls the endpoint every five minutes. Add two
repository secrets under Settings → Secrets and variables → Actions:
| Secret | Value |
|---|---|
APP_URL | https://your-app.vercel.app (no trailing slash) |
CRON_SECRET | the same value as in the app's environment |
Then run it once by hand from the Actions tab — the Run workflow button takes a dry_run
flag, which defaults to true, so the first run reports what it would send without sending
anything. The JSON summary appears on the run page.
Three things to know about GitHub's scheduler:
main, however many times you push it to a feature branch.The alert channels are shared by every producer — new signals, closures and liquidation spikes all land in the same Telegram chat. To receive spikes alone, set an allowlist on the host:
ALERT_KINDS="liqspike"
Valid kinds are signal.opened, signal.confluence, signal.institutional,
signal.closed, liqspike, setup.thrust and setup.ladder; leave it unset
to receive everything. Once set, untagged alerts
are blocked too, so an allowlist stays one as new alert types are added later.
Every scanner in this app renders a page, and until the ledger existed none of
them had a record. /ledger answers the question that makes every other
threshold checkable: which scanners actually produce anything.
.github/workflows/scan-ledger.yml runs hourly (plus once daily for the
engines that only read 1d candles) and calls /api/ledger, which records what
each scanner surfaced and scores the rows whose window has closed. Nothing is
entered by hand.
| Variable | Default | What it does |
|---|---|---|
LEDGER_DEPTH | 60 | Symbols per pass, by volume rank. |
LEDGER_SCORE_LIMIT | 200 | Rows scored per call; the backlog drains across passes. |
Requires DATABASE_URL. Without it the pass still runs and writes nothing, and
the page says so.
What the numbers are. A row is written per setup per bar — keyed on the bar the scan read, so a setup that persists across six passes is one row, not six. Six copies would not be six pieces of evidence; they are one setup counted six times, and they would make every rate a function of how often the cron runs.
Outcomes are measured from the close of the bar the scan read, identically for every scanner — not from whatever entry each one proposes, which would need a fill model. Which threshold came first decides it: a setup that runs 4 ATR in your favour after a 1 ATR move against you is recorded as a loss, because nobody was still in it. Where both fall inside one candle the adverse side is assumed first, which is the pessimistic reading and is chosen deliberately — the optimistic one cannot be checked without tick data, and an unverifiable assumption that favours the product is the kind that never gets revisited.
What they are not. Measured frequencies over whatever has accumulated, not edges and not forecasts. A rate is withheld entirely below 20 scored rows. The ledger also cannot see what the scanners never surfaced, so the claim is always "setups this scanner shows do X", never "setups like this do X".
The two setup scanners push to the same channels, on their own schedule
(.github/workflows/setup-alerts.yml, hourly by default) via
/api/alerts/setups, guarded by the same CRON_SECRET.
ALERT_KINDS="setup.thrust,setup.ladder"
| Variable | Default | What it does |
|---|---|---|
SETUP_ALERT_TIMEFRAME | 1h | Keep the cron schedule in step with it. |
SETUP_ALERT_DEPTH | 80 | Symbols swept, by volume rank. |
SETUP_ALERT_COOLDOWN_MIN | 120 | Per symbol, so one coin cannot spam. |
SETUP_ALERT_MAX_PER_RUN | 5 | Caps a violent session. |
SETUP_ALERT_THRUST_MIN_SCORE | 3 | Checks passed out of five. |
SETUP_ALERT_THRUST_MIN_BOOM_RATE | 0 (off) | See below. |
SETUP_ALERT_THRUST_MIN_PRECEDENT | 5 | Cases needed before the rate filters. |
SETUP_ALERT_LADDER_MIN_BARS | 6 | Steps in the run. |
SETUP_ALERT_LADDER_MIN_R2 | 0.9 | Straightness, 0-1. |
SETUP_ALERT_LADDER_MIN_BODY | 0.5 | Share of bars closing with the run. |
Three things about these alerts are deliberate and worth knowing before tuning them:
Only armed setups are sent. Not the ones that have already expanded,
however good they look in the scanner. By then the level is behind price, so
the alert would be an invitation to chase arriving with the authority of a
notification.
One alert per event, not per sweep. The dedupe key is built from the event's own timestamp — the change of character, or the bar a ladder started on — so a setup that sits at its level for six bars produces one message. The consequence is that a second visit to the same level does not re-alert.
The precedent filter is off by default. SETUP_ALERT_THRUST_MIN_BOOM_RATE
lets you require that a symbol's own history shows follow-through, but the
default does not make that judgement for you. When it is on it applies only to
symbols with at least MIN_PRECEDENT cases: a thin record is no record, not a
bad one, and filtering on it would silently drop every symbol whose history is
simply too short.
The alert body states the precedent as a count with a denominator ("7 of 11 previous reached 3 ATR before losing the level"), never as a percentage. That is not stylistic. An alert is read in two seconds on a lock screen with no surrounding context, which is exactly where "64%" stops being a description of eleven past bars and becomes a belief about the next one.
Every threshold is an env var (see .env.example). The defaults are deliberately strict, because an
alerter that fires a hundred times a day gets muted and is then worse than no alerts at all:
| Variable | Default | What it does |
|---|---|---|
LIQ_ALERT_TIMEFRAME | 5m | Also the floor latency — see below. |
LIQ_ALERT_MIN_SCORE | 70 | Raise for fewer, stronger alerts. |
LIQ_ALERT_MAX_BARS_AGO | 3 | Older spikes are history, not an entry. |
LIQ_ALERT_MIN_REVERSAL_PCT | 0.4 | Requires the turn to have started. |
LIQ_ALERT_MAX_PER_RUN | 5 | Caps a violent session. |
LIQ_ALERT_COOLDOWN_MIN | 45 | Per symbol, so one coin cannot spam. |
Each spike alerts once: the dedupe key is built from the spike bar's own timestamp and enforced by a unique index, so re-reading the same candles on the next sweep sends nothing.
Spikes are detected from closed candles, so an alert is inherently up to one bar behind — on the 5m default, up to ~5 minutes, plus whatever your scheduler adds. Every message states how long ago the spike printed rather than implying it is live.
Genuinely immediate alerting needs Binance's !forceOrder@arr all-market websocket, which streams
real liquidation prints as they happen and would also upgrade forced from inferred to
confirmed (the engine already supports the distinction — it just never receives measured data). A
websocket needs a persistent connection, so that step only makes sense once the worker is deployed
somewhere always-on.
The platform deliberately makes no fixed accuracy claims (no "90% win rate" marketing):
This software is a research/analysis tool, not financial advice. Futures trading carries a substantial risk of loss.