@gonzih/polymarket-arb 1.0.11 → 1.0.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,96 +1,100 @@
1
- export declare const BACKTEST_WINDOW_HOURS = 4;
2
- export declare const BACKTEST_MOMENTUM_THRESHOLD = 0.05;
3
- export type ResolvedMarket = {
1
+ export declare const COINBASE_API = "https://api.exchange.coinbase.com";
2
+ export declare const CLOB_API = "https://clob.polymarket.com";
3
+ export declare const MOMENTUM_THRESHOLD = 0.015;
4
+ export declare const CORRELATION_THRESHOLD = 0.02;
5
+ export declare const CORRELATION_WINDOW_MINUTES = 30;
6
+ export type Candle = [number, number, number, number, number, number];
7
+ export declare const CANDLE_TIME = 0;
8
+ export declare const CANDLE_LOW = 1;
9
+ export declare const CANDLE_HIGH = 2;
10
+ export declare const CANDLE_OPEN = 3;
11
+ export declare const CANDLE_CLOSE = 4;
12
+ export declare const CANDLE_VOL = 5;
13
+ export type CandleSignal = {
14
+ firedAt: number;
15
+ symbol: string;
16
+ direction: "UP" | "DOWN";
17
+ momentum: number;
18
+ price: number;
19
+ confidence: number;
20
+ };
21
+ export type RawTrade = {
22
+ price: string | number;
23
+ timestamp: string | number;
24
+ };
25
+ export type PolymarketMarket = {
4
26
  id: string;
5
27
  conditionId: string;
6
28
  clobTokenId: string;
7
29
  question: string;
30
+ yesPrice: number;
8
31
  volume: number;
9
- startDate: number;
10
- endDate: number;
11
- resolutionTime: number;
12
- resolution: number;
13
- };
14
- export type PricePoint = {
15
- t: number;
16
- p: number;
17
32
  };
18
- export type BacktestSignal = {
19
- firedAt: number;
20
- oddsAtSignal: number;
21
- direction: "YES" | "NO";
22
- momentum: number;
23
- };
24
- export type ClaudeDecision = "BUY_YES" | "BUY_NO" | "PASS" | "ERROR";
25
- export type BacktestResult = {
33
+ export type OddsMove = {
26
34
  marketId: string;
27
35
  question: string;
28
- signalFiredAt: number;
29
- oddsAtSignal: number;
30
- claudeDecision: ClaudeDecision;
31
- claudeLatencyMs: number;
32
- actualResolution: number;
33
- correct: boolean;
34
- kellySizePct: number;
35
- hypotheticalPnl: number;
36
+ oddsChange: number;
37
+ direction: "UP" | "DOWN";
38
+ };
39
+ export type SignalResult = {
40
+ signal: CandleSignal;
41
+ marketsChecked: number;
42
+ correlatedMoves: OddsMove[];
43
+ };
44
+ export type BacktestReport = {
45
+ date: string;
46
+ product: string;
47
+ candlesAnalyzed: number;
48
+ signalsFired: number;
49
+ signalRatePerDay: number;
50
+ marketsChecked: number;
51
+ correlatedSignals: number;
52
+ correlationRate: number;
53
+ signals: SignalResult[];
54
+ claudeInterpretation: string;
36
55
  };
37
- export declare function fetchResolvedMarkets(limit?: number): Promise<ResolvedMarket[]>;
38
56
  /**
39
- * Fetches hourly price history from the CLOB API.
40
- * NOTE (discovered during backtest): The CLOB prices-history endpoint returns
41
- * empty data for resolved/closed markets. Price history is only available for
42
- * currently active markets, and typically has very few data points.
43
- * marketId should be a clobTokenId (the long numeric string from clobTokenIds[0]).
57
+ * Fetch 1-minute (or custom granularity) OHLCV candles from Coinbase REST API.
58
+ * Coinbase returns newest-first; we reverse to chronological order.
44
59
  */
45
- export declare function fetchPriceHistory(marketId: string): Promise<PricePoint[]>;
60
+ export declare function fetchCoinbaseCandles(product?: string, granularity?: number, limit?: number): Promise<Candle[]>;
46
61
  /**
47
- * Calls Claude directly on a resolved market question to probe integration health.
48
- * Used when price history is unavailable and no momentum signals can be replayed.
62
+ * Replay the 1.5% momentum signal logic against Coinbase candle data.
63
+ * Uses per-candle momentum (open→close). Applies 5-minute per-direction cooldown.
49
64
  */
50
- export declare function probeClaudeIntegration(markets: ResolvedMarket[]): Promise<{
51
- success: number;
52
- errors: number;
53
- avgLatencyMs: number;
54
- sample: BacktestResult[];
55
- }>;
65
+ export declare function replaySignals(candles: Candle[], symbol?: string): CandleSignal[];
56
66
  /**
57
- * Replays the EXISTING momentum signal logic against prediction market price history.
58
- * Adapted from SignalEngine in signal.ts: same % change concept, but uses a 4-hour
59
- * window and 5% threshold suited to hourly prediction market data (0-1 price range).
67
+ * Fetch active Polymarket markets from the CLOB API.
68
+ * Handles both array and {data:[]} response shapes.
60
69
  */
61
- export declare function replaySignals(history: PricePoint[]): BacktestSignal[];
70
+ export declare function fetchPolymarketMarkets(limit?: number): Promise<PolymarketMarket[]>;
62
71
  /**
63
- * Kelly Criterion: f* = (p*b - q) / b
64
- * where b = net odds (profit per $ risked), p = win probability, q = 1 - p
65
- * Capped at 10% maximum.
72
+ * Fetch recent trades for a Polymarket market token from the CLOB.
73
+ * Returns empty array on any error.
66
74
  */
67
- export declare function kellySize(odds: number, winProb: number): number;
68
- export declare function computePnl(decision: ClaudeDecision, odds: number, resolution: number, kellySizePct: number): number;
75
+ export declare function fetchMarketTrades(tokenId: string): Promise<RawTrade[]>;
69
76
  /**
70
- * Calls the Claude CLI subprocess. Sends prompt via stdin (not as a positional arg)
71
- * because when spawned with an open stdin pipe the CLI waits for input otherwise.
77
+ * For each signal, check if any Polymarket market moved >2% in odds
78
+ * within `windowMinutes` of the signal firing.
79
+ * tradesByMarket is a pre-fetched map of marketId → trades.
72
80
  */
73
- export declare function askClaude(question: string, odds: number): Promise<{
74
- decision: ClaudeDecision;
75
- latencyMs: number;
76
- }>;
77
- export interface BacktestReport {
78
- marketsAnalyzed: number;
79
- signalsFired: number;
80
- claudeSuccesses: number;
81
- claudeErrors: number;
82
- avgLatencyMs: number;
83
- maxLatencyMs: number;
84
- buyYesTotal: number;
85
- buyYesCorrect: number;
86
- buyNoTotal: number;
87
- buyNoCorrect: number;
88
- passCount: number;
89
- avgKellyPct: number;
90
- totalPnl: number;
91
- results: BacktestResult[];
92
- }
93
- export declare function generateReport(results: BacktestResult[], marketsAnalyzed: number): BacktestReport;
94
- export declare function formatReport(report: BacktestReport, date: string): string;
95
- export declare function writeReport(text: string, date: string): string;
81
+ export declare function findCorrelatedMoves(signal: CandleSignal, markets: PolymarketMarket[], tradesByMarket: Record<string, RawTrade[]>, oddsThreshold?: number, windowMinutes?: number): OddsMove[];
82
+ /**
83
+ * Build a human-readable signal log for Claude interpretation.
84
+ */
85
+ export declare function buildSignalLog(results: SignalResult[]): string;
86
+ /**
87
+ * Spawn claude --print and ask for signal pattern analysis.
88
+ * Returns Claude's response text or a fallback message on failure.
89
+ */
90
+ export declare function askClaude(signalLog: string): Promise<string>;
91
+ /**
92
+ * Render the full backtest report as Markdown.
93
+ */
94
+ export declare function generateMarkdownReport(report: BacktestReport): string;
95
+ /**
96
+ * Write a report to disk. Creates `dir` if it doesn't exist.
97
+ * Returns the path written.
98
+ */
99
+ export declare function writeReport(text: string, date: string, dir?: string): string;
96
100
  //# sourceMappingURL=backtest.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"backtest.d.ts","sourceRoot":"","sources":["../src/backtest.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"backtest.d.ts","sourceRoot":"","sources":["../src/backtest.ts"],"names":[],"mappings":"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"}
package/dist/backtest.js CHANGED
@@ -1,12 +1,72 @@
1
1
  import { spawn } from "child_process";
2
2
  import fs from "fs";
3
+ import path from "path";
3
4
  import { log } from "./logger.js";
4
- const GAMMA_API = "https://gamma-api.polymarket.com";
5
- const CLOB_API = "https://clob.polymarket.com";
6
- // Momentum parameters adapted for prediction market hourly price data
7
- // (0-1 range, slower-moving than crypto ticks)
8
- export const BACKTEST_WINDOW_HOURS = 4;
9
- export const BACKTEST_MOMENTUM_THRESHOLD = 0.05; // 5% move over 4h
5
+ export const COINBASE_API = "https://api.exchange.coinbase.com";
6
+ export const CLOB_API = "https://clob.polymarket.com";
7
+ export const MOMENTUM_THRESHOLD = 0.015; // 1.5% per candle (open→close)
8
+ export const CORRELATION_THRESHOLD = 0.02; // 2% odds move
9
+ export const CORRELATION_WINDOW_MINUTES = 30;
10
+ export const CANDLE_TIME = 0;
11
+ export const CANDLE_LOW = 1;
12
+ export const CANDLE_HIGH = 2;
13
+ export const CANDLE_OPEN = 3;
14
+ export const CANDLE_CLOSE = 4;
15
+ export const CANDLE_VOL = 5;
16
+ /**
17
+ * Fetch 1-minute (or custom granularity) OHLCV candles from Coinbase REST API.
18
+ * Coinbase returns newest-first; we reverse to chronological order.
19
+ */
20
+ export async function fetchCoinbaseCandles(product = "BTC-USD", granularity = 60, limit = 300) {
21
+ try {
22
+ const url = `${COINBASE_API}/products/${encodeURIComponent(product)}/candles?granularity=${granularity}&limit=${limit}`;
23
+ const res = await fetch(url);
24
+ if (!res.ok) {
25
+ log("warn", { source: "backtest", event: "coinbase_candles_error", status: res.status });
26
+ return [];
27
+ }
28
+ const data = (await res.json());
29
+ // Reverse so index 0 is oldest
30
+ return data.reverse();
31
+ }
32
+ catch (err) {
33
+ log("warn", { source: "backtest", event: "coinbase_candles_exception", error: String(err) });
34
+ return [];
35
+ }
36
+ }
37
+ /**
38
+ * Replay the 1.5% momentum signal logic against Coinbase candle data.
39
+ * Uses per-candle momentum (open→close). Applies 5-minute per-direction cooldown.
40
+ */
41
+ export function replaySignals(candles, symbol = "BTC-USD") {
42
+ const signals = [];
43
+ const COOLDOWN_MS = 5 * 60 * 1000;
44
+ const lastSignalTime = { UP: 0, DOWN: 0 };
45
+ for (const candle of candles) {
46
+ const open = candle[CANDLE_OPEN];
47
+ const close = candle[CANDLE_CLOSE];
48
+ const ts = candle[CANDLE_TIME];
49
+ if (open === 0)
50
+ continue;
51
+ const momentum = (close - open) / open;
52
+ if (Math.abs(momentum) < MOMENTUM_THRESHOLD)
53
+ continue;
54
+ const direction = momentum > 0 ? "UP" : "DOWN";
55
+ const firedAt = ts * 1000;
56
+ if (firedAt - lastSignalTime[direction] < COOLDOWN_MS)
57
+ continue;
58
+ lastSignalTime[direction] = firedAt;
59
+ signals.push({
60
+ firedAt,
61
+ symbol,
62
+ direction,
63
+ momentum,
64
+ price: close,
65
+ confidence: Math.min(1, Math.abs(momentum) / (MOMENTUM_THRESHOLD * 2)),
66
+ });
67
+ }
68
+ return signals;
69
+ }
10
70
  function parseJsonField(field) {
11
71
  if (Array.isArray(field))
12
72
  return field;
@@ -17,354 +77,201 @@ function parseJsonField(field) {
17
77
  return [];
18
78
  }
19
79
  }
20
- export async function fetchResolvedMarkets(limit = 100) {
21
- const sixMonthsAgo = Date.now() - 180 * 24 * 60 * 60 * 1000;
22
- // Use end_date_min to fetch recent markets without scanning thousands of pages
23
- const sixMonthsAgoDate = new Date(sixMonthsAgo).toISOString().slice(0, 10);
24
- const results = [];
25
- let offset = 0;
26
- const batchSize = 100;
27
- while (results.length < limit) {
28
- const url = `${GAMMA_API}/markets?closed=true&limit=${batchSize}&offset=${offset}&end_date_min=${sixMonthsAgoDate}`;
29
- let markets;
30
- try {
31
- const res = await fetch(url);
32
- if (!res.ok) {
33
- log("warn", { source: "backtest", event: "fetch_resolved_error", status: res.status });
34
- break;
35
- }
36
- markets = (await res.json());
37
- }
38
- catch (err) {
39
- log("warn", { source: "backtest", event: "fetch_resolved_exception", error: String(err) });
40
- break;
80
+ /**
81
+ * Fetch active Polymarket markets from the CLOB API.
82
+ * Handles both array and {data:[]} response shapes.
83
+ */
84
+ export async function fetchPolymarketMarkets(limit = 20) {
85
+ try {
86
+ const url = `${CLOB_API}/markets?active=true&closed=false&limit=${limit}`;
87
+ const res = await fetch(url);
88
+ if (!res.ok) {
89
+ log("warn", { source: "backtest", event: "polymarket_markets_error", status: res.status });
90
+ return [];
41
91
  }
42
- if (markets.length === 0)
43
- break;
44
- for (const m of markets) {
45
- const volume = Number(m.volumeNum ?? m.volume ?? 0);
46
- if (volume < 50_000)
47
- continue;
48
- const endDate = m.endDate ? new Date(m.endDate).getTime() : 0;
49
- if (endDate < sixMonthsAgo || endDate === 0)
50
- continue;
51
- // Only include cleanly resolved markets (YES price = 0 or 1)
92
+ const raw = (await res.json());
93
+ const markets = Array.isArray(raw) ? raw : (raw.data ?? []);
94
+ return markets
95
+ .map((m) => {
52
96
  const prices = parseJsonField(m.outcomePrices ?? []).map(Number);
53
- if (prices.length < 2)
54
- continue;
55
- const yesPrice = prices[0];
56
- if (yesPrice !== 0 && yesPrice !== 1)
57
- continue;
58
- // Parse YES outcome clobTokenId for CLOB price history
97
+ const yesPrice = prices[0] ?? 0.5;
59
98
  const tokenIds = parseJsonField(m.clobTokenIds ?? "[]");
60
- const clobTokenId = tokenIds[0] ?? "";
61
- results.push({
62
- id: m.id,
63
- conditionId: m.conditionId ?? m.id,
64
- clobTokenId,
99
+ return {
100
+ id: m.id ?? "",
101
+ conditionId: m.conditionId ?? m.id ?? "",
102
+ clobTokenId: tokenIds[0] ?? "",
65
103
  question: m.question ?? "",
66
- volume,
67
- startDate: m.startDate ? new Date(m.startDate).getTime() : 0,
68
- endDate,
69
- resolutionTime: m.resolutionTime ? new Date(m.resolutionTime).getTime() : endDate,
70
- resolution: yesPrice === 1 ? 1 : 0,
71
- });
72
- if (results.length >= limit)
73
- break;
74
- }
75
- offset += batchSize;
76
- if (markets.length < batchSize)
77
- break; // no more pages
104
+ yesPrice,
105
+ volume: Number(m.volumeNum ?? m.volume ?? 0),
106
+ };
107
+ })
108
+ .filter((m) => m.id && m.question && m.volume > 10_000);
109
+ }
110
+ catch (err) {
111
+ log("warn", { source: "backtest", event: "polymarket_markets_exception", error: String(err) });
112
+ return [];
78
113
  }
79
- log("info", {
80
- source: "backtest",
81
- event: "resolved_markets_fetched",
82
- count: results.length,
83
- });
84
- return results;
85
114
  }
86
115
  /**
87
- * Fetches hourly price history from the CLOB API.
88
- * NOTE (discovered during backtest): The CLOB prices-history endpoint returns
89
- * empty data for resolved/closed markets. Price history is only available for
90
- * currently active markets, and typically has very few data points.
91
- * marketId should be a clobTokenId (the long numeric string from clobTokenIds[0]).
116
+ * Fetch recent trades for a Polymarket market token from the CLOB.
117
+ * Returns empty array on any error.
92
118
  */
93
- export async function fetchPriceHistory(marketId) {
119
+ export async function fetchMarketTrades(tokenId) {
94
120
  try {
95
- const url = `${CLOB_API}/prices-history?market=${encodeURIComponent(marketId)}&interval=1h&fidelity=60`;
121
+ const url = `${CLOB_API}/trades?market=${encodeURIComponent(tokenId)}&limit=500`;
96
122
  const res = await fetch(url);
97
123
  if (!res.ok)
98
124
  return [];
99
- const data = (await res.json());
100
- const history = Array.isArray(data) ? data : (data.history ?? []);
101
- return history.sort((a, b) => a.t - b.t);
125
+ const raw = (await res.json());
126
+ return Array.isArray(raw) ? raw : (raw.data ?? []);
102
127
  }
103
128
  catch {
104
129
  return [];
105
130
  }
106
131
  }
107
132
  /**
108
- * Calls Claude directly on a resolved market question to probe integration health.
109
- * Used when price history is unavailable and no momentum signals can be replayed.
133
+ * For each signal, check if any Polymarket market moved >2% in odds
134
+ * within `windowMinutes` of the signal firing.
135
+ * tradesByMarket is a pre-fetched map of marketId → trades.
110
136
  */
111
- export async function probeClaudeIntegration(markets) {
112
- const sample = markets.slice(0, 5);
113
- const results = [];
114
- let totalLatency = 0;
115
- let errors = 0;
116
- for (const market of sample) {
117
- // Use last-known odds as 0.5 (unknown pre-resolution for closed markets)
118
- const odds = 0.5;
119
- const { decision, latencyMs } = await askClaude(market.question, odds);
120
- totalLatency += latencyMs;
121
- if (decision === "ERROR")
122
- errors++;
123
- const correct = decision === "BUY_YES"
124
- ? market.resolution === 1
125
- : decision === "BUY_NO"
126
- ? market.resolution === 0
127
- : false;
128
- results.push({
129
- marketId: market.id,
130
- question: market.question,
131
- signalFiredAt: 0,
132
- oddsAtSignal: odds,
133
- claudeDecision: decision,
134
- claudeLatencyMs: latencyMs,
135
- actualResolution: market.resolution,
136
- correct,
137
- kellySizePct: 0,
138
- hypotheticalPnl: 0,
137
+ export function findCorrelatedMoves(signal, markets, tradesByMarket, oddsThreshold = CORRELATION_THRESHOLD, windowMinutes = CORRELATION_WINDOW_MINUTES) {
138
+ const windowStartSec = signal.firedAt / 1000;
139
+ const windowEndSec = windowStartSec + windowMinutes * 60;
140
+ const correlated = [];
141
+ for (const market of markets) {
142
+ const trades = tradesByMarket[market.id] ?? [];
143
+ const windowTrades = trades.filter((t) => {
144
+ const ts = Number(t.timestamp);
145
+ const tsSec = ts < 1e12 ? ts : Math.floor(ts / 1000);
146
+ return tsSec >= windowStartSec && tsSec <= windowEndSec;
139
147
  });
140
- }
141
- return {
142
- success: sample.length - errors,
143
- errors,
144
- avgLatencyMs: sample.length > 0 ? totalLatency / sample.length : 0,
145
- sample: results,
146
- };
147
- }
148
- /**
149
- * Replays the EXISTING momentum signal logic against prediction market price history.
150
- * Adapted from SignalEngine in signal.ts: same % change concept, but uses a 4-hour
151
- * window and 5% threshold suited to hourly prediction market data (0-1 price range).
152
- */
153
- export function replaySignals(history) {
154
- const signals = [];
155
- if (history.length < BACKTEST_WINDOW_HOURS + 1)
156
- return signals;
157
- let lastSignalAtMs = 0;
158
- const COOLDOWN_MS = 12 * 60 * 60 * 1000; // 12-hour cooldown between signals per market
159
- for (let i = BACKTEST_WINDOW_HOURS; i < history.length; i++) {
160
- const windowStart = history[i - BACKTEST_WINDOW_HOURS];
161
- const current = history[i];
162
- if (windowStart.p === 0)
148
+ if (windowTrades.length < 2)
163
149
  continue;
164
- const momentum = (current.p - windowStart.p) / windowStart.p;
165
- if (Math.abs(momentum) < BACKTEST_MOMENTUM_THRESHOLD)
166
- continue;
167
- const tMs = current.t * 1000;
168
- if (tMs - lastSignalAtMs < COOLDOWN_MS)
169
- continue;
170
- lastSignalAtMs = tMs;
171
- signals.push({
172
- firedAt: tMs,
173
- oddsAtSignal: current.p,
174
- direction: momentum > 0 ? "YES" : "NO",
175
- momentum,
176
- });
150
+ const priceStart = Number(windowTrades[0].price);
151
+ const priceEnd = Number(windowTrades[windowTrades.length - 1].price);
152
+ const oddsChange = priceEnd - priceStart;
153
+ if (Math.abs(oddsChange) >= oddsThreshold) {
154
+ correlated.push({
155
+ marketId: market.id,
156
+ question: market.question,
157
+ oddsChange: Math.abs(oddsChange),
158
+ direction: oddsChange > 0 ? "UP" : "DOWN",
159
+ });
160
+ }
177
161
  }
178
- return signals;
162
+ return correlated;
179
163
  }
180
164
  /**
181
- * Kelly Criterion: f* = (p*b - q) / b
182
- * where b = net odds (profit per $ risked), p = win probability, q = 1 - p
183
- * Capped at 10% maximum.
165
+ * Build a human-readable signal log for Claude interpretation.
184
166
  */
185
- export function kellySize(odds, winProb) {
186
- if (odds <= 0 || odds >= 1)
187
- return 0;
188
- const b = (1 - odds) / odds; // net odds
189
- const q = 1 - winProb;
190
- const kelly = (winProb * b - q) / b;
191
- return Math.max(0, Math.min(0.1, kelly));
192
- }
193
- export function computePnl(decision, odds, resolution, kellySizePct) {
194
- if (decision === "PASS" || decision === "ERROR")
195
- return 0;
196
- const betYes = decision === "BUY_YES";
197
- const won = betYes ? resolution === 1 : resolution === 0;
198
- const betOdds = betYes ? odds : 1 - odds;
199
- if (won) {
200
- // Profit per $ = (1 - betOdds) / betOdds
201
- return kellySizePct * ((1 - betOdds) / betOdds);
167
+ export function buildSignalLog(results) {
168
+ if (results.length === 0) {
169
+ return "No signals fired in the analysis window. Momentum threshold (1.5%) not crossed in recent candles.";
170
+ }
171
+ const correlated = results.filter((r) => r.correlatedMoves.length > 0).length;
172
+ const lines = [
173
+ `Total signals: ${results.length}`,
174
+ `Correlated with Polymarket moves >2%: ${correlated}/${results.length}`,
175
+ `Correlation rate: ${((correlated / results.length) * 100).toFixed(1)}%`,
176
+ "",
177
+ "Signal Log:",
178
+ ];
179
+ for (const r of results) {
180
+ const ts = new Date(r.signal.firedAt).toISOString();
181
+ const pct = (r.signal.momentum * 100).toFixed(2);
182
+ const corrStr = r.correlatedMoves.length > 0
183
+ ? r.correlatedMoves
184
+ .map((m) => `${m.question.slice(0, 40)} (${(m.oddsChange * 100).toFixed(1)}% ${m.direction})`)
185
+ .join("; ")
186
+ : "no correlated moves";
187
+ lines.push(` [${ts}] ${r.signal.direction} ${pct}% @ $${r.signal.price.toFixed(0)} | conf=${r.signal.confidence.toFixed(2)} | ${corrStr}`);
202
188
  }
203
- return -kellySizePct;
189
+ return lines.join("\n");
204
190
  }
205
191
  /**
206
- * Calls the Claude CLI subprocess. Sends prompt via stdin (not as a positional arg)
207
- * because when spawned with an open stdin pipe the CLI waits for input otherwise.
192
+ * Spawn claude --print and ask for signal pattern analysis.
193
+ * Returns Claude's response text or a fallback message on failure.
208
194
  */
209
- export async function askClaude(question, odds) {
210
- const start = Date.now();
211
- const prompt = `Market: ${question}\nCurrent odds: ${(odds * 100).toFixed(1)}% YES\nSignal: momentum spike detected\nShould we bet YES or NO? Respond with: BUY_YES, BUY_NO, or PASS`;
195
+ export async function askClaude(signalLog) {
196
+ const prompt = `Given these signal firings and Polymarket odds movements, what patterns do you see? ` +
197
+ `Which signal types (high momentum, news-boosted, specific time windows) correlate best with market moves? ` +
198
+ `What threshold would maximize signal quality?\n\n${signalLog}`;
212
199
  return new Promise((resolve) => {
213
200
  const proc = spawn("claude", ["--print", "--model", "claude-haiku-4-5-20251001"], {
214
201
  env: { ...process.env },
215
202
  stdio: ["pipe", "pipe", "pipe"],
216
203
  });
217
- // Send prompt via stdin then close it so claude knows there is no more input
218
204
  proc.stdin.write(prompt);
219
205
  proc.stdin.end();
220
206
  let stdout = "";
221
- let stderr = "";
222
207
  let timedOut = false;
223
208
  proc.stdout.on("data", (chunk) => {
224
209
  stdout += chunk.toString();
225
210
  });
226
- proc.stderr.on("data", (chunk) => {
227
- stderr += chunk.toString();
228
- });
211
+ proc.stderr.on("data", () => { }); // suppress stderr noise
229
212
  const timer = setTimeout(() => {
230
213
  timedOut = true;
231
214
  proc.kill("SIGTERM");
232
- }, 30_000);
215
+ }, 60_000);
233
216
  proc.on("close", (code) => {
234
217
  clearTimeout(timer);
235
- const latencyMs = Date.now() - start;
236
218
  if (timedOut || code !== 0) {
237
- const err = timedOut
238
- ? "timeout after 30s"
239
- : `exit code ${code}${stderr ? ": " + stderr.slice(0, 200) : ""}`;
240
- log("warn", { source: "backtest", event: "claude_error", error: err });
241
- resolve({ decision: "ERROR", latencyMs });
219
+ resolve("(Claude interpretation unavailable — subprocess error or timeout)");
242
220
  return;
243
221
  }
244
- const text = stdout.toUpperCase();
245
- let decision = "PASS";
246
- if (text.includes("BUY_YES"))
247
- decision = "BUY_YES";
248
- else if (text.includes("BUY_NO"))
249
- decision = "BUY_NO";
250
- log("info", {
251
- source: "backtest",
252
- event: "claude_decision",
253
- question: question.slice(0, 60),
254
- decision,
255
- latencyMs,
256
- });
257
- resolve({ decision, latencyMs });
222
+ resolve(stdout.trim() || "(No interpretation returned)");
258
223
  });
259
- proc.on("error", (err) => {
224
+ proc.on("error", () => {
260
225
  clearTimeout(timer);
261
- const latencyMs = Date.now() - start;
262
- log("warn", { source: "backtest", event: "claude_error", error: String(err) });
263
- resolve({ decision: "ERROR", latencyMs });
226
+ resolve("(Claude interpretation unavailable spawn error)");
264
227
  });
265
228
  });
266
229
  }
267
- export function generateReport(results, marketsAnalyzed) {
268
- const claudeErrors = results.filter((r) => r.claudeDecision === "ERROR").length;
269
- const claudeSuccesses = results.filter((r) => r.claudeDecision !== "ERROR").length;
270
- const latencies = results.map((r) => r.claudeLatencyMs).filter((l) => l > 0);
271
- const avgLatencyMs = latencies.length > 0 ? latencies.reduce((a, b) => a + b, 0) / latencies.length : 0;
272
- const maxLatencyMs = latencies.length > 0 ? Math.max(...latencies) : 0;
273
- const buyYes = results.filter((r) => r.claudeDecision === "BUY_YES");
274
- const buyNo = results.filter((r) => r.claudeDecision === "BUY_NO");
275
- const passes = results.filter((r) => r.claudeDecision === "PASS");
276
- const kellyValues = results.filter((r) => r.kellySizePct > 0).map((r) => r.kellySizePct);
277
- const avgKellyPct = kellyValues.length > 0 ? kellyValues.reduce((a, b) => a + b, 0) / kellyValues.length : 0;
278
- const totalPnl = results.reduce((sum, r) => sum + r.hypotheticalPnl, 0);
279
- return {
280
- marketsAnalyzed,
281
- signalsFired: results.length,
282
- claudeSuccesses,
283
- claudeErrors,
284
- avgLatencyMs,
285
- maxLatencyMs,
286
- buyYesTotal: buyYes.length,
287
- buyYesCorrect: buyYes.filter((r) => r.correct).length,
288
- buyNoTotal: buyNo.length,
289
- buyNoCorrect: buyNo.filter((r) => r.correct).length,
290
- passCount: passes.length,
291
- avgKellyPct,
292
- totalPnl,
293
- results,
294
- };
295
- }
296
- export function formatReport(report, date) {
297
- const totalDecisions = report.buyYesTotal + report.buyNoTotal;
298
- const totalCorrect = report.buyYesCorrect + report.buyNoCorrect;
299
- const winRate = totalDecisions > 0 ? (totalCorrect / totalDecisions) * 100 : 0;
300
- const signalRate = report.marketsAnalyzed > 0
301
- ? (report.signalsFired / report.marketsAnalyzed) * 100
302
- : 0;
303
- const yesAcc = report.buyYesTotal > 0
304
- ? `${report.buyYesCorrect}/${report.buyYesTotal} (${((report.buyYesCorrect / report.buyYesTotal) * 100).toFixed(1)}%)`
305
- : "0/0 (n/a)";
306
- const noAcc = report.buyNoTotal > 0
307
- ? `${report.buyNoCorrect}/${report.buyNoTotal} (${((report.buyNoCorrect / report.buyNoTotal) * 100).toFixed(1)}%)`
308
- : "0/0 (n/a)";
309
- const claudeStatus = report.claudeErrors === 0
310
- ? ` ✓ All ${report.claudeSuccesses} calls succeeded`
311
- : ` ✓ ${report.claudeSuccesses} calls succeeded\n ✗ ${report.claudeErrors} error${report.claudeErrors !== 1 ? "s" : ""}`;
312
- let verdict;
313
- if (totalDecisions === 0) {
314
- verdict =
315
- "INSUFFICIENT DATA: No actionable signals. Either no price history from API, " +
316
- "signals never crossed the 5% threshold, or all signals fired after market resolution.";
317
- }
318
- else if (totalDecisions < 5) {
319
- verdict =
320
- `TOO FEW TRADES: Only ${totalDecisions} trade${totalDecisions !== 1 ? "s" : ""} — ` +
321
- "cannot distinguish edge from luck. Need 30+ trades for statistical significance.";
322
- }
323
- else if (winRate > 60) {
324
- verdict =
325
- `POSSIBLE EDGE: Win rate ${winRate.toFixed(1)}% exceeds 50% baseline. ` +
326
- `P&L: ${report.totalPnl >= 0 ? "+" : ""}${(report.totalPnl * 100).toFixed(1)}% of bankroll. ` +
327
- "Needs larger sample (30+ trades) to confirm.";
328
- }
329
- else if (winRate > 50) {
330
- verdict =
331
- `WEAK SIGNAL: Win rate ${winRate.toFixed(1)}% slightly above baseline. ` +
332
- "Cannot yet distinguish from noise. More data needed.";
333
- }
334
- else {
335
- verdict =
336
- `NO EDGE DETECTED: Win rate ${winRate.toFixed(1)}% at or below 50% baseline. ` +
337
- "Current signal parameters not predictive on this historical data.";
338
- }
339
- const lines = [
340
- "=== POLYMARKET-ARB BACKTEST REPORT ===",
341
- `Date: ${date}`,
342
- "",
343
- `Markets analyzed: ${report.marketsAnalyzed}`,
344
- `Signals fired: ${report.signalsFired} (${signalRate.toFixed(1)}% of markets)`,
345
- `Claude Code: ${report.claudeSuccesses}/${report.signalsFired} decisions returned (${report.claudeErrors} error${report.claudeErrors !== 1 ? "s" : ""})`,
346
- `Claude latency: avg ${(report.avgLatencyMs / 1000).toFixed(1)}s, max ${(report.maxLatencyMs / 1000).toFixed(1)}s`,
230
+ /**
231
+ * Render the full backtest report as Markdown.
232
+ */
233
+ export function generateMarkdownReport(report) {
234
+ const signalRows = report.signals.length > 0
235
+ ? report.signals.map((r) => {
236
+ const ts = new Date(r.signal.firedAt).toISOString().replace("T", " ").slice(0, 19);
237
+ const mom = `${(r.signal.momentum * 100).toFixed(2)}%`;
238
+ const marketMove = r.correlatedMoves.length > 0
239
+ ? r.correlatedMoves.map((m) => `${(m.oddsChange * 100).toFixed(1)}%`).join(", ")
240
+ : "—";
241
+ return `| ${ts} | ${r.signal.symbol} | ${mom} | ${r.signal.direction} | ${marketMove} |`;
242
+ })
243
+ : ["| — | — | — | — | — |"];
244
+ return [
245
+ `# Polymarket Backtest — ${report.date}`,
347
246
  "",
348
- "SIGNAL ACCURACY:",
349
- ` BUY_YES decisions: ${report.buyYesTotal} → correct: ${yesAcc}`,
350
- ` BUY_NO decisions: ${report.buyNoTotal} → correct: ${noAcc}`,
351
- ` PASS decisions: ${report.passCount}`,
247
+ "## Summary",
248
+ `- Candles analyzed: ${report.candlesAnalyzed}`,
249
+ `- Signals fired: ${report.signalsFired}`,
250
+ `- Signal rate: ${report.signalRatePerDay.toFixed(1)} per day`,
251
+ `- Markets checked per signal: ${report.marketsChecked}`,
252
+ `- Correlated moves (signal + market move >2%): ${report.correlatedSignals}`,
253
+ `- Correlation rate: ${report.correlationRate.toFixed(1)}%`,
352
254
  "",
353
- "EDGE vs RANDOM:",
354
- ` Win rate: ${winRate.toFixed(1)}% (random baseline: 50%)`,
355
- ` Avg Kelly size: ${(report.avgKellyPct * 100).toFixed(1)}% of bankroll`,
356
- ` Hypothetical total P&L: ${report.totalPnl >= 0 ? "+" : ""}${(report.totalPnl * 100).toFixed(1)}% of bankroll over ${report.marketsAnalyzed} markets`,
255
+ "## Signal Log",
256
+ "| Time | Symbol | Momentum | Direction | Market Move |",
257
+ "|------|--------|----------|-----------|-------------|",
258
+ ...signalRows,
357
259
  "",
358
- "CLAUDE CODE INTEGRATION:",
359
- claudeStatus,
260
+ "## Interpretation",
261
+ report.claudeInterpretation,
360
262
  "",
361
- `VERDICT: ${verdict}`,
362
- ];
363
- return lines.join("\n");
263
+ ].join("\n");
364
264
  }
365
- export function writeReport(text, date) {
366
- const reportPath = `backtest-report-${date}.md`;
367
- fs.writeFileSync(reportPath, text + "\n");
265
+ /**
266
+ * Write a report to disk. Creates `dir` if it doesn't exist.
267
+ * Returns the path written.
268
+ */
269
+ export function writeReport(text, date, dir = "research") {
270
+ if (!fs.existsSync(dir)) {
271
+ fs.mkdirSync(dir, { recursive: true });
272
+ }
273
+ const reportPath = path.join(dir, `backtest-results-${date}.md`);
274
+ fs.writeFileSync(reportPath, text);
368
275
  return reportPath;
369
276
  }
370
277
  //# sourceMappingURL=backtest.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"backtest.js","sourceRoot":"","sources":["../src/backtest.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"backtest.js","sourceRoot":"","sources":["../src/backtest.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"backtestRunner.d.ts","sourceRoot":"","sources":["../src/backtestRunner.ts"],"names":[],"mappings":"AAoBA,wBAAsB,WAAW,IAAI,OAAO,CAAC,IAAI,CAAC,CA+HjD"}
1
+ {"version":3,"file":"backtestRunner.d.ts","sourceRoot":"","sources":["../src/backtestRunner.ts"],"names":[],"mappings":"AAoBA,wBAAsB,WAAW,IAAI,OAAO,CAAC,IAAI,CAAC,CAiFjD"}
@@ -1,129 +1,74 @@
1
- import { fetchResolvedMarkets, fetchPriceHistory, replaySignals, askClaude, kellySize, computePnl, generateReport, formatReport as formatBaseReport, writeReport, probeClaudeIntegration, } from "./backtest.js";
2
- import { log } from "./logger.js";
3
- const MARKETS_TO_FETCH = 50;
4
- // At most one Claude call per market to keep runtime reasonable
5
- const MAX_SIGNALS_PER_MARKET = 1;
1
+ import { fetchCoinbaseCandles, replaySignals, fetchPolymarketMarkets, fetchMarketTrades, findCorrelatedMoves, askClaude, buildSignalLog, generateMarkdownReport, writeReport, } from "./backtest.js";
2
+ const PRODUCT = "BTC-USD";
3
+ const GRANULARITY = 60; // 1-minute candles
4
+ const CANDLE_LIMIT = 300; // ~5 hours of data
5
+ const POLYMARKET_MARKETS = 20;
6
6
  export async function runBacktest() {
7
7
  const date = new Date().toISOString().slice(0, 10);
8
8
  console.log("=== POLYMARKET-ARB BACKTESTING HARNESS ===");
9
- console.log(`Fetching up to ${MARKETS_TO_FETCH} resolved markets (volume > $50k, last 6 months)...`);
10
- const markets = await fetchResolvedMarkets(MARKETS_TO_FETCH);
11
- console.log(`Fetched ${markets.length} qualifying markets\n`);
12
- if (markets.length === 0) {
13
- console.error("ERROR: No resolved markets found.\n" +
9
+ console.log(`Fetching ${CANDLE_LIMIT} × ${GRANULARITY}s candles for ${PRODUCT}...`);
10
+ const candles = await fetchCoinbaseCandles(PRODUCT, GRANULARITY, CANDLE_LIMIT);
11
+ if (candles.length === 0) {
12
+ console.error("ERROR: No candles returned from Coinbase REST API.\n" +
14
13
  "Possible causes:\n" +
15
- " • GAMMA API unreachable\n" +
16
- " • No markets with volume > $50k resolved in last 6 months\n" +
17
- " • outcomePrices not cleanly 0 or 1 (market still settling)");
14
+ " • API rate-limited or unreachable\n" +
15
+ " • Network error");
18
16
  process.exit(1);
19
17
  }
20
- const results = [];
21
- let marketsWithHistory = 0;
22
- let marketsNoHistory = 0;
23
- let marketsNoSignal = 0;
24
- for (let i = 0; i < markets.length; i++) {
25
- const market = markets[i];
26
- process.stdout.write(`\r[${i + 1}/${markets.length}] ${market.question.slice(0, 55)}...`);
27
- // Use the YES clobTokenId for price history
28
- const tokenId = market.clobTokenId || market.conditionId;
29
- const history = await fetchPriceHistory(tokenId);
30
- if (history.length < 5) {
31
- marketsNoHistory++;
32
- continue;
33
- }
34
- marketsWithHistory++;
35
- const signals = replaySignals(history).slice(0, MAX_SIGNALS_PER_MARKET);
36
- if (signals.length === 0) {
37
- marketsNoSignal++;
38
- continue;
39
- }
40
- for (const signal of signals) {
41
- // Skip signals that fired at or after resolution — unfair look-ahead
42
- if (signal.firedAt >= market.resolutionTime)
43
- continue;
44
- const { decision, latencyMs } = await askClaude(market.question, signal.oddsAtSignal);
45
- const betOdds = decision === "BUY_YES" ? signal.oddsAtSignal : 1 - signal.oddsAtSignal;
46
- // Assume modest 65% win probability as prior when signal fires
47
- const WIN_PROB_PRIOR = 0.65;
48
- const kellySizePct = decision !== "PASS" && decision !== "ERROR"
49
- ? kellySize(betOdds, WIN_PROB_PRIOR)
50
- : 0;
51
- const pnl = computePnl(decision, signal.oddsAtSignal, market.resolution, kellySizePct);
52
- const correct = decision === "BUY_YES"
53
- ? market.resolution === 1
54
- : decision === "BUY_NO"
55
- ? market.resolution === 0
56
- : false;
57
- results.push({
58
- marketId: market.id,
59
- question: market.question,
60
- signalFiredAt: signal.firedAt,
61
- oddsAtSignal: signal.oddsAtSignal,
62
- claudeDecision: decision,
63
- claudeLatencyMs: latencyMs,
64
- actualResolution: market.resolution,
65
- correct,
66
- kellySizePct,
67
- hypotheticalPnl: pnl,
68
- });
69
- log("info", {
70
- source: "backtest",
71
- event: "result",
72
- question: market.question.slice(0, 60),
73
- decision,
74
- oddsAtSignal: signal.oddsAtSignal.toFixed(3),
75
- resolution: market.resolution,
76
- correct,
77
- pnl: pnl.toFixed(4),
78
- });
18
+ console.log(`Fetched ${candles.length} candles`);
19
+ const signals = replaySignals(candles, PRODUCT);
20
+ console.log(`Signals fired: ${signals.length} (threshold: 1.5% per candle)`);
21
+ console.log(`\nFetching ${POLYMARKET_MARKETS} active Polymarket markets...`);
22
+ const markets = await fetchPolymarketMarkets(POLYMARKET_MARKETS);
23
+ console.log(`Fetched ${markets.length} qualifying markets (volume > $10k)`);
24
+ // Pre-fetch trades for all markets once, then reuse across signals
25
+ const tradesByMarket = {};
26
+ if (signals.length > 0 && markets.length > 0) {
27
+ console.log(`Pre-fetching trades for ${markets.length} markets...`);
28
+ for (let i = 0; i < markets.length; i++) {
29
+ const market = markets[i];
30
+ if (market.clobTokenId) {
31
+ process.stdout.write(`\r [${i + 1}/${markets.length}] ${market.question.slice(0, 50)}`);
32
+ tradesByMarket[market.id] = await fetchMarketTrades(market.clobTokenId);
33
+ }
79
34
  }
35
+ process.stdout.write("\n");
80
36
  }
81
- process.stdout.write("\n\n");
82
- console.log(`Price history: ${marketsWithHistory}/${markets.length} markets had history, ` +
83
- `${marketsNoHistory} had no/insufficient data, ` +
84
- `${marketsNoSignal} had history but no signal fired`);
85
- // ── Claude integration probe ──────────────────────────────────────────────
86
- // Always run this to verify the subprocess works, regardless of signals.
87
- console.log("\nRunning Claude integration probe (5 markets)...");
88
- const probe = await probeClaudeIntegration(markets);
89
- console.log(`Claude probe: ${probe.success}/5 calls succeeded, ` +
90
- `${probe.errors} errors, avg latency ${(probe.avgLatencyMs / 1000).toFixed(1)}s`);
91
- // Add probe results to the report if no signal-based results exist
92
- const reportResults = results.length > 0 ? results : probe.sample;
93
- const report = generateReport(reportResults, markets.length);
94
- const reportText = buildFullReport(report, probe, marketsNoHistory, markets.length, date);
95
- console.log("\n" + reportText);
37
+ const results = signals.map((signal) => {
38
+ const correlatedMoves = findCorrelatedMoves(signal, markets, tradesByMarket);
39
+ return {
40
+ signal,
41
+ marketsChecked: markets.length,
42
+ correlatedMoves,
43
+ };
44
+ });
45
+ const correlatedCount = results.filter((r) => r.correlatedMoves.length > 0).length;
46
+ const candleMinutes = (candles.length * GRANULARITY) / 60;
47
+ const signalRatePerDay = candleMinutes > 0 ? (signals.length / candleMinutes) * 24 * 60 : 0;
48
+ console.log(`\nResults:`);
49
+ console.log(` Signals fired: ${signals.length}`);
50
+ console.log(` Signals with correlated Polymarket moves: ${correlatedCount}/${signals.length}`);
51
+ console.log(` Correlation rate: ${signals.length > 0 ? ((correlatedCount / signals.length) * 100).toFixed(1) : "0.0"}%`);
52
+ const signalLog = buildSignalLog(results);
53
+ console.log("\nAsking Claude for interpretation...");
54
+ const claudeInterpretation = await askClaude(signalLog);
55
+ console.log("Claude responded.");
56
+ const report = {
57
+ date,
58
+ product: PRODUCT,
59
+ candlesAnalyzed: candles.length,
60
+ signalsFired: signals.length,
61
+ signalRatePerDay,
62
+ marketsChecked: markets.length,
63
+ correlatedSignals: correlatedCount,
64
+ correlationRate: signals.length > 0 ? (correlatedCount / signals.length) * 100 : 0,
65
+ signals: results,
66
+ claudeInterpretation,
67
+ };
68
+ const reportText = generateMarkdownReport(report);
96
69
  const reportPath = writeReport(reportText, date);
97
70
  console.log(`\nReport written to: ${reportPath}`);
98
- if (probe.errors > 0) {
99
- console.warn(`\nWARNING: ${probe.errors} Claude call(s) failed.\n` +
100
- "Check that CLAUDE_CODE_OAUTH_TOKEN or ANTHROPIC_AUTH_TOKEN is set.");
101
- }
102
- }
103
- function buildFullReport(report, probe, marketsNoHistory, marketsTotal, date) {
104
- let text = formatBaseReport(report, date);
105
- if (marketsNoHistory === marketsTotal) {
106
- text +=
107
- "\n\nAPI FINDING: CLOB /prices-history endpoint returned empty data for all " +
108
- marketsTotal +
109
- " resolved markets.\n" +
110
- "Investigation results:\n" +
111
- " • GET /prices-history returns {history:[]} for all closed/resolved markets\n" +
112
- " • Active markets: price history exists but only ~2 data points (insufficient for 4h window)\n" +
113
- " • The end_date_min filter works to find recent markets efficiently\n" +
114
- " • Recommendation: use a dedicated historical data provider (Dune Analytics, TheGraph) for future backtests\n";
115
- }
116
- text +=
117
- "\n\nCLAUDE INTEGRATION PROBE (5 markets, no momentum signal required):\n" +
118
- ` ${probe.success}/5 calls succeeded (${probe.errors} errors)\n` +
119
- ` Avg latency: ${(probe.avgLatencyMs / 1000).toFixed(1)}s\n`;
120
- for (const r of probe.sample) {
121
- const icon = r.claudeDecision === "ERROR" ? "✗" : "✓";
122
- text +=
123
- ` ${icon} "${r.question.slice(0, 50)}" → ${r.claudeDecision} ` +
124
- `(${(r.claudeLatencyMs / 1000).toFixed(1)}s, resolved: ${r.actualResolution === 1 ? "YES" : "NO"})\n`;
125
- }
126
- return text;
71
+ console.log("\n" + reportText);
127
72
  }
128
73
  // Run when invoked directly (not imported)
129
74
  const selfPath = process.argv[1] ?? "";
@@ -1 +1 @@
1
- {"version":3,"file":"backtestRunner.js","sourceRoot":"","sources":["../src/backtestRunner.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"backtestRunner.js","sourceRoot":"","sources":["../src/backtestRunner.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,oBAAoB,EACpB,aAAa,EACb,sBAAsB,EACtB,iBAAiB,EACjB,mBAAmB,EACnB,SAAS,EACT,cAAc,EACd,sBAAsB,EACtB,WAAW,GAIZ,MAAM,eAAe,CAAC;AAEvB,MAAM,OAAO,GAAG,SAAS,CAAC;AAC1B,MAAM,WAAW,GAAG,EAAE,CAAC,CAAC,mBAAmB;AAC3C,MAAM,YAAY,GAAG,GAAG,CAAC,CAAC,mBAAmB;AAC7C,MAAM,kBAAkB,GAAG,EAAE,CAAC;AAE9B,MAAM,CAAC,KAAK,UAAU,WAAW;IAC/B,MAAM,IAAI,GAAG,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;IAEnD,OAAO,CAAC,GAAG,CAAC,4CAA4C,CAAC,CAAC;IAC1D,OAAO,CAAC,GAAG,CAAC,YAAY,YAAY,MAAM,WAAW,iBAAiB,OAAO,KAAK,CAAC,CAAC;IAEpF,MAAM,OAAO,GAAG,MAAM,oBAAoB,CAAC,OAAO,EAAE,WAAW,EAAE,YAAY,CAAC,CAAC;IAC/E,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACzB,OAAO,CAAC,KAAK,CACX,sDAAsD;YACpD,oBAAoB;YACpB,uCAAuC;YACvC,mBAAmB,CACtB,CAAC;QACF,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC;IACD,OAAO,CAAC,GAAG,CAAC,WAAW,OAAO,CAAC,MAAM,UAAU,CAAC,CAAC;IAEjD,MAAM,OAAO,GAAG,aAAa,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;IAChD,OAAO,CAAC,GAAG,CAAC,kBAAkB,OAAO,CAAC,MAAM,+BAA+B,CAAC,CAAC;IAE7E,OAAO,CAAC,GAAG,CAAC,cAAc,kBAAkB,+BAA+B,CAAC,CAAC;IAC7E,MAAM,OAAO,GAAG,MAAM,sBAAsB,CAAC,kBAAkB,CAAC,CAAC;IACjE,OAAO,CAAC,GAAG,CAAC,WAAW,OAAO,CAAC,MAAM,qCAAqC,CAAC,CAAC;IAE5E,mEAAmE;IACnE,MAAM,cAAc,GAA+B,EAAE,CAAC;IACtD,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QAC7C,OAAO,CAAC,GAAG,CAAC,2BAA2B,OAAO,CAAC,MAAM,aAAa,CAAC,CAAC;QACpE,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE,CAAC;YACxC,MAAM,MAAM,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;YAC1B,IAAI,MAAM,CAAC,WAAW,EAAE,CAAC;gBACvB,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,QAAQ,CAAC,GAAG,CAAC,IAAI,OAAO,CAAC,MAAM,KAAK,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC;gBACzF,cAAc,CAAC,MAAM,CAAC,EAAE,CAAC,GAAG,MAAM,iBAAiB,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC;YAC1E,CAAC;QACH,CAAC;QACD,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;IAC7B,CAAC;IAED,MAAM,OAAO,GAAmB,OAAO,CAAC,GAAG,CAAC,CAAC,MAAM,EAAE,EAAE;QACrD,MAAM,eAAe,GAAG,mBAAmB,CAAC,MAAM,EAAE,OAAO,EAAE,cAAc,CAAC,CAAC;QAC7E,OAAO;YACL,MAAM;YACN,cAAc,EAAE,OAAO,CAAC,MAAM;YAC9B,eAAe;SAChB,CAAC;IACJ,CAAC,CAAC,CAAC;IAEH,MAAM,eAAe,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,eAAe,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,MAAM,CAAC;IACnF,MAAM,aAAa,GAAG,CAAC,OAAO,CAAC,MAAM,GAAG,WAAW,CAAC,GAAG,EAAE,CAAC;IAC1D,MAAM,gBAAgB,GACpB,aAAa,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,MAAM,GAAG,aAAa,CAAC,GAAG,EAAE,GAAG,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;IAErE,OAAO,CAAC,GAAG,CAAC,YAAY,CAAC,CAAC;IAC1B,OAAO,CAAC,GAAG,CAAC,oBAAoB,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;IAClD,OAAO,CAAC,GAAG,CAAC,+CAA+C,eAAe,IAAI,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;IAChG,OAAO,CAAC,GAAG,CAAC,uBAAuB,OAAO,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,eAAe,GAAG,OAAO,CAAC,MAAM,CAAC,GAAG,GAAG,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,KAAK,GAAG,CAAC,CAAC;IAE1H,MAAM,SAAS,GAAG,cAAc,CAAC,OAAO,CAAC,CAAC;IAE1C,OAAO,CAAC,GAAG,CAAC,uCAAuC,CAAC,CAAC;IACrD,MAAM,oBAAoB,GAAG,MAAM,SAAS,CAAC,SAAS,CAAC,CAAC;IACxD,OAAO,CAAC,GAAG,CAAC,mBAAmB,CAAC,CAAC;IAEjC,MAAM,MAAM,GAAmB;QAC7B,IAAI;QACJ,OAAO,EAAE,OAAO;QAChB,eAAe,EAAE,OAAO,CAAC,MAAM;QAC/B,YAAY,EAAE,OAAO,CAAC,MAAM;QAC5B,gBAAgB;QAChB,cAAc,EAAE,OAAO,CAAC,MAAM;QAC9B,iBAAiB,EAAE,eAAe;QAClC,eAAe,EAAE,OAAO,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,eAAe,GAAG,OAAO,CAAC,MAAM,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC,CAAC;QAClF,OAAO,EAAE,OAAO;QAChB,oBAAoB;KACrB,CAAC;IAEF,MAAM,UAAU,GAAG,sBAAsB,CAAC,MAAM,CAAC,CAAC;IAClD,MAAM,UAAU,GAAG,WAAW,CAAC,UAAU,EAAE,IAAI,CAAC,CAAC;IACjD,OAAO,CAAC,GAAG,CAAC,wBAAwB,UAAU,EAAE,CAAC,CAAC;IAClD,OAAO,CAAC,GAAG,CAAC,IAAI,GAAG,UAAU,CAAC,CAAC;AACjC,CAAC;AAED,2CAA2C;AAC3C,MAAM,QAAQ,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC;AACvC,IAAI,QAAQ,CAAC,QAAQ,CAAC,mBAAmB,CAAC,IAAI,QAAQ,CAAC,QAAQ,CAAC,mBAAmB,CAAC,EAAE,CAAC;IACrF,WAAW,EAAE,CAAC,KAAK,CAAC,CAAC,GAAY,EAAE,EAAE;QACnC,OAAO,CAAC,KAAK,CAAC,kBAAkB,EAAE,GAAG,CAAC,CAAC;QACvC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC,CAAC,CAAC;AACL,CAAC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@gonzih/polymarket-arb",
3
- "version": "1.0.11",
3
+ "version": "1.0.13",
4
4
  "description": "Claude-powered Polymarket arbitrage bot — BTC/ETH momentum signal + AI trade analysis",
5
5
  "keywords": [
6
6
  "polymarket",