mirror of
https://github.com/theodore-song/polymarket-analyst.git
synced 2026-08-24 13:08:10 +00:00
Require forward proof for sports capital
This commit is contained in:
@@ -1,6 +1,7 @@
|
||||
const GAMMA = "https://gamma-api.polymarket.com";
|
||||
const CLOB = "https://clob.polymarket.com";
|
||||
const MARKET_LIMIT = Math.max(500, Math.min(5000, Number(process.env.SPORTS_FAVORITE_MARKETS || 3000)));
|
||||
const MARKET_SKIP = Math.max(0, Math.min(20000, Number(process.env.SPORTS_FAVORITE_SKIP || 0)));
|
||||
const CONCURRENCY = Math.max(1, Math.min(12, Number(process.env.SPORTS_FAVORITE_CONCURRENCY || 10)));
|
||||
const COST = Math.max(0, Math.min(0.10, Number(process.env.SPORTS_FAVORITE_COST_CENTS || 5) / 100));
|
||||
const MAX_STALENESS_HOURS = Math.max(1, Math.min(12, Number(process.env.SPORTS_FAVORITE_MAX_STALENESS_HOURS || 3)));
|
||||
@@ -59,8 +60,9 @@ function gameStart(raw) {
|
||||
return timestamp(raw.gameStartTime || raw.eventStartTime || event.startTime || event.eventDate);
|
||||
}
|
||||
|
||||
async function fetchMarkets(limit) {
|
||||
async function fetchMarkets(limit, skip = 0) {
|
||||
const markets = [], seen = new Set();
|
||||
let eligibleSeen = 0;
|
||||
let cursor = "";
|
||||
while (markets.length < limit) {
|
||||
const params = new URLSearchParams({ closed: "true", order: "closedTime", ascending: "false", limit: "100", include_tag: "true" });
|
||||
@@ -75,6 +77,7 @@ async function fetchMarkets(limit) {
|
||||
if (!id || seen.has(id) || labels[0] !== "yes" || labels[1] !== "no" || tokens.length !== 2 || finalYes == null
|
||||
|| !startsAt || !closedAt || !sportsMarket(raw)) continue;
|
||||
seen.add(id);
|
||||
if (eligibleSeen++ < skip) continue;
|
||||
markets.push({ id, question: raw.question || "", eventKey: String(raw.events?.[0]?.id || id), event: raw.events?.[0]?.title || "",
|
||||
tokenId: tokens[0], finalYes, startsAt, closedAt, marketType: String(raw.sportsMarketType || "unknown") });
|
||||
if (markets.length >= limit) break;
|
||||
@@ -126,7 +129,7 @@ for (const leadHours of [12, 18, 24, 30, 36]) {
|
||||
}
|
||||
}
|
||||
|
||||
const markets = await fetchMarkets(MARKET_LIMIT);
|
||||
const markets = await fetchMarkets(MARKET_LIMIT, MARKET_SKIP);
|
||||
const histories = await mapLimit(markets, CONCURRENCY, async (market) => {
|
||||
const data = await fetchJson(`${CLOB}/prices-history?market=${encodeURIComponent(market.tokenId)}&interval=max&fidelity=60`);
|
||||
const points = (data.history || []).map((point) => ({ t: Number(point.t), p: Number(point.p) }))
|
||||
@@ -177,7 +180,7 @@ const closest = evaluated.filter((row) => row.train.events >= 25 && row.validati
|
||||
.sort((a, b) => Math.min(b.train.lower, b.validation.lower, b.holdout.lower)
|
||||
- Math.min(a.train.lower, a.validation.lower, a.holdout.lower));
|
||||
|
||||
console.log(JSON.stringify({ generatedAt: new Date().toISOString(), requestedMarkets: MARKET_LIMIT, sportsMarkets: markets.length,
|
||||
console.log(JSON.stringify({ generatedAt: new Date().toISOString(), requestedMarkets: MARKET_LIMIT, skippedEligibleMarkets: MARKET_SKIP, sportsMarkets: markets.length,
|
||||
historiesWithData: usable.length, failures: histories.filter((row) => row?.error).length,
|
||||
methodology: { selection: "most recently closed eligible Yes/No sports markets", decisionAnchor: "published game start",
|
||||
historyFidelityMinutes: 60, maxPriceStalenessHours: MAX_STALENESS_HOURS, modeledCostCents: COST * 100,
|
||||
|
||||
@@ -8,10 +8,13 @@ const workflow = fs.readFileSync(new URL("../.github/workflows/autonomous-cycle.
|
||||
const runner = fs.readFileSync(new URL("./run-autonomous-cycle.mjs", import.meta.url), "utf8");
|
||||
const resolutionAudit = JSON.parse(fs.readFileSync(new URL("../research/resolution-week-no-audit.json", import.meta.url), "utf8"));
|
||||
const sportsContestAudit = JSON.parse(fs.readFileSync(new URL("../research/sports-contest-no-exploration-audit.json", import.meta.url), "utf8"));
|
||||
const sportsDisjointAudit = JSON.parse(fs.readFileSync(new URL("../research/sports-contest-no-disjoint-10000-audit.json", import.meta.url), "utf8"));
|
||||
const adaptiveAudit = JSON.parse(fs.readFileSync(new URL("../research/adaptive-strategy-64-audit.json", import.meta.url), "utf8"));
|
||||
const sportsEvaluator = fs.readFileSync(new URL("./evaluate-sports-favorites.mjs", import.meta.url), "utf8");
|
||||
const build = Number(index.match(/const BUILD_VERSION = (\d+);/)?.[1]);
|
||||
|
||||
assert.equal(build, 121);
|
||||
assert.equal(build, 122);
|
||||
assert.match(index, /Adaptive strategy 64 · durable evidence · build 122/);
|
||||
assert.deepEqual([...ALLOWED_RUNTIME_KEYS].sort(), ["pma_agents_v2", "pma_suggestions_v5"]);
|
||||
assert.match(index, /function collectPublicRuntimeItems\(\)/);
|
||||
assert.match(index, /const PUBLIC_RUNTIME_KEYS=Object\.freeze\(\[AGENTS_KEY,SUG_KEY\]\)/);
|
||||
@@ -126,6 +129,15 @@ assert.ok(sportsContestAudit.corrected_5000_market_result.validation.lower_95 <
|
||||
assert.equal(sportsContestAudit.production_constraints.initial_position_pct, 0.5);
|
||||
assert.equal(sportsContestAudit.production_constraints.total_lane_cap_pct, 3);
|
||||
assert.equal(sportsContestAudit.production_constraints.exact_entry_fee_required, true);
|
||||
assert.equal(sportsDisjointAudit.status, "zero-capital-forward-shadow");
|
||||
assert.equal(sportsDisjointAudit.recent_5000.holdout_rules_passing, 0);
|
||||
assert.equal(sportsDisjointAudit.older_disjoint_5000.validation_rules_passing, 0);
|
||||
assert.ok(sportsDisjointAudit.recent_5000.closest_rule.holdout_lower_90 < 0);
|
||||
assert.ok(sportsDisjointAudit.older_disjoint_5000.closest_rule.holdout_lower_90 < 0);
|
||||
assert.equal(sportsDisjointAudit.decision.capital_enabled, false);
|
||||
assert.equal(sportsDisjointAudit.decision.initial_position_pct, 0);
|
||||
assert.match(sportsEvaluator, /const MARKET_SKIP =/);
|
||||
assert.match(sportsEvaluator, /fetchMarkets\(MARKET_LIMIT, MARKET_SKIP\)/);
|
||||
assert.equal(adaptiveAudit.strategy, 64);
|
||||
assert.equal(adaptiveAudit.fetched_markets, 500);
|
||||
assert.deepEqual(adaptiveAudit.probation_rule_ids, []);
|
||||
@@ -134,6 +146,9 @@ assert.ok(adaptiveAudit.horizons.every((row) => row.validation_selected === 0 &&
|
||||
assert.match(index, /function sportsContestKey\(m\)/);
|
||||
assert.match(index, /function sportsContestNoSuggestions\(markets\)/);
|
||||
assert.match(index, /const SPORTS_FAVORITE_MAX_NEW_PER_CYCLE=1;/);
|
||||
assert.match(index, /const SPORTS_FAVORITE_PILOT_POSITION_PCT=0;/);
|
||||
assert.match(index, /capitalRequiresForwardPromotion:true,boundedExploration:false/);
|
||||
assert.match(index, /initialStateIsZeroCapitalShadow:/);
|
||||
assert.match(index, /function compactDecisionForPublic\(decision\)/);
|
||||
assert.match(index, /delete out\.learning\.buckets/);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user