PolyClaw Trading’s deterministic engine is built around eight named stages —Documentation Index
Fetch the complete documentation index at: https://mintlify.com/deniszidbaev-cmyk/polyclaw-trading/llms.txt
Use this file to discover all available pages before exploring further.
fetch, candles, analyze, signal, bankroll, validate, execute, and report. Each stage is independently runnable, reads its inputs from runtime/ JSON files, and writes its outputs back there. No stage skips a failed predecessor or continues from malformed or stale upstream state.
Entry points
There are two ways to invoke a stage. Package CLI (polyclaw-engine) — the installed console script from the polyclaw_engine package:
scripts/run_pipeline.py) — launches each stage as a separate process so JSON files remain the only inter-process contract. This is the Windows-first recommended entry point for full pipeline and loop execution:
.env.local for configuration. The subprocess runner additionally pins LIVE_TRADING=0 when you use the dry-run mode, regardless of what the environment says.
The 8 pipeline stages
fetch — Discover active BTC markets
Queries the Polymarket Gamma API with keyset pagination, joins YES/NO outcomes by label, validates question semantics, and fetches public YES-token price history. Results are saved to The
runtime/.--fixture flag accepts a path to a JSON file. When provided, the stage reads market data from the file instead of contacting Polymarket. Fixtures are forbidden in live mode.candles — Build pseudo-OHLC candles
Constructs UTC-aligned 5-minute and 15-minute pseudo-OHLC candles from the price history written by The engine uses
fetch. The resulting candle sets are saved to runtime/.5m candles for execution signals and 15m candles for confirmation. Both must meet minimum quality thresholds (MIN_CANDLES_5M, MIN_CANDLES_15M) before the pipeline continues.analyze — Compute indicators and quality
Reads the candle data and computes all indicators needed for signal generation: candle quality score, EMA8/EMA21, RSI14, ATR14, sample-density Point of Control (POC), realized volatility (population std of the last 20 close-to-close returns), and deterministic pattern evidence. Results are saved to Indicators use exact Wilder smoothing for RSI and ATR. EMA uses
runtime/market_analysis.json.alpha = 2 / (period + 1) with first-observation seeding. Non-finite numbers, bad OHLC geometry, and non-monotonic timestamps all fail closed.signal — Generate YES/NO/HOLD decisions
Applies deterministic scoring across trend, RSI zone, candle patterns, candle quality, market quality, POC context, and timeframe alignment to produce a The confidence formula is:Any signal with confidence below
YES, NO, or HOLD direction with a confidence score. Every decision is persisted to runtime/decisions.json.MIN_EXECUTION_CONFIDENCE (default 0.72) becomes HOLD and is written to runtime/manual_review.json instead of proceeding to execution.bankroll — Refresh risk and capital state
Reads the runtime trade registry and recomputes the current reserve balance, drawdown mode status, daily risk limits, daily notional limits, and open-exposure totals. Output is saved to Drawdown multipliers are
runtime/bankroll_state.json.1.00 (normal), 0.50 (reduced), and 0.25 (critical). Critical mode activates at twice DRAWDOWN_TRIGGER_PCT; recovery to normal requires drawdown to fall to or below DRAWDOWN_RECOVERY_PCT.validate — Size position and check all gates
Sizes the position against every active capital cap (per-trade risk, daily risk, daily notional, open exposure, free balance minus reserve) and then reruns a fresh set of semantic, quality, expiry, cooldown, duplicate, and risk checks. Only a decision that clears every gate proceeds to Position sizing takes the minimum of: the confidence-interpolated maximum, the bankroll-risk cap, the position cap, remaining daily risk, remaining daily notional, remaining exposure, and free balance. A failed gate writes the reason to
execute.runtime/trade_gate_status.json and stops the cycle.execute — Dry-run or invoke PolyClaw
In dry-run mode (default, Every execution — dry or live — is journaled under
LIVE_TRADING=0), records the execution plan to runtime/executions/YYYYMMDD.json without sending any order. In live mode (LIVE_TRADING=1), rereads fresh bankroll, risk, registry, expiry, semantic, pattern, quality, and cooldown state immediately before launching the PolyClaw subprocess.runtime/executions/. If PolyClaw succeeds on-chain but the CLOB sell fails, the engine records partial_failure, reserves the market, and activates cooldown. Offline fixtures are forbidden in live mode.Orchestration commands
Beyond running individual stages, both entry points support higher-level orchestration:cycle — Run all 8 stages once
Executes the complete pipeline from fetch through report in sequence:
--fixture to supply an offline market file for the fetch stage:
loop — Repeat cycle on interval
Runs cycle repeatedly, sleeping LOOP_INTERVAL_SEC seconds (default 300) between iterations:
--max-cycles 0 (the default) means unlimited. Set a positive integer to cap the number of cycles for supervision or automated test runs.
audit — Run the unittest test suite
Discovers and runs all tests under tests/ using Python’s built-in unittest:
analysis-cycle vs trade-cycle
The subprocess runner (scripts/run_pipeline.py) exposes two partial-pipeline shortcuts:
| Mode | Stages run | Purpose |
|---|---|---|
analysis-cycle | fetch, candles, analyze, signal | Signal generation only — no bankroll, validation, or execution |
trade-cycle | fetch through execute (skips report) | Full trading pass without the terminal report |
dry-run | All 8 stages, LIVE_TRADING forced to 0 | Safe offline verification |
Runtime JSON contract
Every stage reads and writes underruntime/. Key files:
| File | Written by | Contains |
|---|---|---|
runtime/decisions.json | signal | YES/NO/HOLD decisions with confidence scores |
runtime/bankroll_state.json | bankroll | Equity, reserve, drawdown, exposure |
runtime/market_analysis.json | analyze | Indicators, patterns, quality scores |
runtime/trade_gate_status.json | validate | Gate result, block reason, daily counters |
runtime/executions/YYYYMMDD.json | execute | Daily execution ledger (dry and live) |
runtime/manual_review.json | signal | HOLD decisions that need operator review |
schema_version, stage, generated_at, and data fields. Atomic writes use a unique temporary sibling, flush with fsync, then os.replace. Malformed JSON, wrong schema version, stale timestamps, non-finite numbers, and invalid price bounds always fail closed.