v12-dfs
io.github.Jorgeperez0825/v12-dfsVersion 1.0.0AI-driven DFS lineup optimizer for MLB & NBA — build FanDuel & DraftKings lineups via MCP.
Status
Responds281 msAnswered our handshake without sign-in.- Last checked
- Nov 14, 2026, 14:38 UTC
- Latency
- 281 ms
- Remotes responding
- 1 of 1
- Sign-in
- API key
- Hosting
- Hosted outside the EU (detected)
- Registry data as of
- Nov 14, 2026, 22:14 UTC
Data from the official MCP Registry, checked by run.zero. How we check
Connect
Streamable HTTP
https://v12dfs-production.up.railway.app/mcpResponds281 msNo sign-in
Claude Code
claude mcp add --transport http v12-dfs https://v12dfs-production.up.railway.app/mcp --header 'X-API-Key: <YOUR_X_API_KEY>'Replace <YOUR_X_API_KEY> before running.
Claude Desktop and claude.ai
Settings > Connectors > Add custom connector
Name: v12-dfs
Remote MCP server URL: https://v12dfs-production.up.railway.app/mcp
This server expects the header X-API-Key.Cursor
{
"mcpServers": {
"v12-dfs": {
"url": "https://v12dfs-production.up.railway.app/mcp",
"headers": {
"X-API-Key": "<YOUR_X_API_KEY>"
}
}
}
}Replace <YOUR_X_API_KEY> before running.
VS Code
code --add-mcp '{"name":"v12-dfs","type":"http","url":"https://v12dfs-production.up.railway.app/mcp","headers":{"X-API-Key":"<YOUR_X_API_KEY>"}}'Replace <YOUR_X_API_KEY> before running.
Built your own server? run.zero hosts MCP servers on European infrastructure.
Tools
35 tools
Read-only | Idempotent | Open world | ||
|---|---|---|---|---|
admin_issue_keyIssue Key
Idempotently issue a user's API key and ALWAYS return the paste-able
connect block. Returns the email's existing active key (or mints one) so a
user keeps a single key across dashboard reloads; with rotate=true, revokes
the existing keys and mints a fresh one. Admin-gated — the dashboard's
per-user provision route (which verifies the user's Firebase token) calls
this server-side, never the browser.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**Example Response:**
```json
{
"api_key": "Api Key",
"tier": "Tier",
"limits": {}
}
```
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
agent_guideAgent Guide
Self-serve onboarding: connect any agent (Claude/MCP or REST) to drive the
V12 motor, the same engine the dashboard agent uses. No auth. Returns
copy-paste MCP + REST config with a PLACEHOLDER key, the endpoint map, and the
generate body fields. Operators: issue each user their OWN key via
POST /v1/admin/create-key — never share one key.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json | Not declared | Not declared | Not declared | Not declared |
betting_agent_guideBetting Agent Guide
How any agent uses the MLB betting tools + how to read the output.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json | Not declared | Not declared | Not declared | Not declared |
betting_analyze_propAnalyze Prop
Model a single player's prop vs tonight's FanDuel line -> edge.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_best_betsBest Bets
THE board sweep — scans EVERY main prop market (HR/RBI/hit/total_bases/
2+hits/stolen_base) in one call and returns the top edges across all of them,
not just home runs. Power props carry the Savant validation (CONFIRMED power
ranked above neutral/noise). Use this for an open 'what's hot / best plays /
what do you recommend tonight' so you NEVER conclude off a single-market scan.
A SCREEN vs the vig line — validate with CLV; game-side value is separate
(betting_sharp / betting_game_model).
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_build_parlayBuild Parlay
Deterministic parlay analysis for BOTH leg shapes. Body:
{legs:[...], ticket_odds?}. PROP legs {name, prop, threshold} keep the
legacy correlation-aware EV. GAME-side legs (ML / run line / total / team
total / F5, selected by the `market` field) — the slips users actually
paste — are priced from the CURRENT de-vigged market at that exact market/
line (canonical team resolution), falling back to the market-anchored run
model for totals; per-leg fair prob + edge vs the slip's price, combined
payout / breakeven / fair prob / EV under a documented independence
assumption. Legs sharing a game are flagged correlated=true and get a
correlation_warning INSTEAD of a combined edge. ticket_odds (the slip's
printed combined price) is verified vs the leg product — >2% off flags
ticket_odds_mismatch (the slip was misread; do not trust the numbers).
NEVER estimate a parlay in prose — this endpoint is the math.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_cross_bookCross Book
Cross-book value: FanDuel vs DraftKings (DK pulled via ESPN's public API,
no key/WS). LINE_SHOP (the books hang different numbers — take the easier
side) and PRICE_SHOP (better price, same line) are CONFIRMED edges, no model
needed. Arbitrage is NOT auto-reported (needs over/under sides, which ESPN
doesn't label). Overnight only pitcher_strikeouts overlaps; richer markets
appear near game time.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_game_linesGame Lines
GAME markets — moneyline / run total / run line for today's MLB games. This
answers the 'quién gana / cuántas carreras / pronóstico Yankees vs Toronto'
questions that player props CAN'T (V12 used to just refuse them). Optional
team filter ('Yankees', 'NYY'). MARKET data from ESPN's public scoreboard,
surfaced as-is — V12 has NO game-outcome model, so this is the book's own
number, never a fabricated prediction. A book may not have posted a game yet
(fields null) — say so, don't invent a line.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_game_modelGame Model
MODEL the GAME run markets — TEAM TOTALS (over/under) and NRFI/YRFI — vs
the FanDuel line, MARKET-ANCHORED: expected_runs = the book's de-vigged
implied mean + 0.25×(structural model − book), and every edge is computed vs
the FAIR (de-vigged) probability, never the raw vig price. The structural
inputs (season runs/game, opposing STARTER + BULLPEN run factors, park;
negative-binomial tails) supply only the tilt. Entries with anchored=false /
model_only=true carry edge=null — present them as context, NEVER as value.
A SCREEN vs the market, not a lock — validate with CLV. For raw lines on
every market use betting_market.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_log_betLog Bet
Record a bet you placed (per user) so we can track P&L + CLV over time.
Body: {uid, market, selection, odds (American), stake, line?, prop?, team?,
game?, book?}. Append-only — this is the evidence base that PROVES edge.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_marketMarket
FULL FanDuel market board for a team's game — EVERY market with real odds +
de-vig fair price, so NO market question goes unanswered. Game lines (ML /
total / run line), FIRST 5 INNINGS (F5), TEAM TOTALS, NRFI/YRFI, alternate
lines, AND the full player-prop menu (HR / 2+ HR / hit / 2+ hits / RBI /
2+ RBI / run / single / double / triple / total bases / stolen base / K).
The book's market surfaced as-is (no model). For our model edge on a prop,
follow up with betting_analyze_prop.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_market_moversMarket Movers
MARKET pattern (not model opinion): how FanDuel lines MOVED today, from the
captured snapshots. A line that shortened = money coming in (sharp/news); a
drift = money off. This is the 'obvious opportunity' signal — market-confirmed,
independent of our unproven model. Needs accumulated capture; thin → thin.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_matchupMatchup
GROUNDING — the real game for a team today: probable pitchers + the POSTED
lineup (ACTUAL player names from MLB statsapi) + the market line + the CONTEXT
a pro reasons with: home-plate UMPIRE (strike zone → totals/Ks), the INJURY
report (who's OUT / Day-To-Day), and BULLPEN health (ERA / blown saves). Call
this BEFORE naming any player or discussing a game. Name ONLY the players this
returns — never a roster from memory (that is how the agent ends up naming
players who aren't on the team).
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_my_betsMy Bets
A user's bet history + P&L / CLV summary. avg_clv_pct > 0 over time = you're
beating the closing line = real edge (the only durable proof).
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_player_formPlayer Form
Streak / splits / recent form for any player ('racha de X').
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_scan_edgesScan Edges
Tonight's prop board ranked by model edge (VALUE first).
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_settle_betSettle Bet
Settle a logged bet. Body: {uid, bet_id, result: won|lost|push,
closing_odds?}. closing_odds lets us compute CLV (did you beat the close).
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
betting_sharpSharp
SHARP value — FanDuel vs PINNACLE (the sharpest book, ~2% hold). Pinnacle's
de-vigged line ≈ TRUE probability, so this is the most reliable value signal in
the kit, NO model needed: edge_vs_sharp = FD's price minus the sharp's true
prob; POSITIVE means FanDuel pays MORE than fair (real value vs the market).
Plus total line-shop. Pinnacle only lists UPCOMING games (gone once started).
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
contest_adviceContest Advice
Advice for a concrete contest name. Resolves the name against the LIVE
lobby FIRST so a real live contest is never reported missing (the curated
registry is only a subset — that was the "$800 Wed MLB Home Run no existe"
bug), then layers registry strategy advice on top when a template matches.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
contest_semaforoContest Semaforo
VIP-only: per-contest play/skip verdict from the owner's verified P&L
bands + structure gates + rake/fill math. See core/data/contest_semaforo.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
fill_templateFill Template
Fill a downloaded FanDuel/DK entries-template with already-generated
lineups WITHOUT re-running the optimizer — the MCP-callable equivalent of the
dashboard's fill_template. Keeps each entry row's leading columns (entry_id,
contest_id, fee) and replaces the roster-slot columns with a lineup's upload
tokens, cycling lineups if there are more entry rows than lineups.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
generate_lineupsGenerate Lineups
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**Example Response:**
```json
{
"status": "Status",
"generated_at": "Generated At",
"warnings": [],
"exposures": {},
"lineups": []
}
```
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
get_slate_playersGet Slate Players Endpoint
Get the V12 player pool for a specific slate ID.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
health_checkHealth
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**Example Response:**
```json
{
"status": "Status",
"version": "Version",
"timestamp": "Timestamp"
}
``` | Not declared | Not declared | Not declared | Not declared |
health_v12Health V12
Deep health check for the V12 pipeline. Surfaces:
- last nightly regression run (pass/fail + per-slate deltas)
- regression baseline metadata
- recent preflight blockers (if any cached)
No auth required — monitoring endpoint.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json | Not declared | Not declared | Not declared | Not declared |
late_swapLate Swap Entries
FanDuel NBA late swap: re-solve the OPEN slots of your existing entries; locked players stay in their slot.
Send the FanDuel entries CSV for the slate (after the first tip: the 'Edit entries' download; before lock:
the entries-upload template). A player whose game has started keeps his exact column; every other slot is
re-solved on fresh projections and OUT news with the salary cap and 4-per-team rule over the WHOLE lineup.
Returns the same file with only those cells changed (`csv`, upload it at FanDuel > Edit entries) and a
per-entry diff. Started slates are hidden by list_slates(playable=true); pass the slate_id from
list_slates(playable=false), or omit it to use the FanDuel fixture id inside the file. NBA FanDuel classic only.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**Example Response:**
```json
{
"status": "Status",
"csv": "Csv",
"filename": "Filename",
"slate_id": 1,
"fd_slate_id": "Fd Slate Id",
"date": "Date",
"salary_cap": 1,
"layout": "Layout",
"mode": "Mode",
"lock_buffer_minutes": 1,
"entries_total": 1,
"entries_changed": 1,
"entries_unchanged": 1,
"entries_infeasible": 1,
"per_entry": [
{
"entry_id": "Entry Id",
"contest_id": "Contest Id",
"contest_name": "Contest Name",
"status": "Status",
"reason": "Reason",
"locked": [
{
"col": 1,
"label": "Label",
"player_id": "Player Id",
"name": "Name"
}
],
"swaps": [
{
"col": 1,
"label": "Label",
"in_id": "In Id",
"in_name": "In Name"
}
],
"proj_before": 1.0,
"gain": 1.0
}
],
"started_games": [
"string"
],
"closing_games": [
"string"
],
"open_games": [
"string"
],
"evaluated_at_utc": "Evaluated At Utc",
"solves": 1,
"warnings": [
"string"
],
"note": "Note"
}
```
**422**: Validation Error | Not declared | Not declared | Not declared | Not declared |
list_contestsContest Registry
List contest strategy registry entries for agents and the dashboard.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
list_live_contestsLive Contests
Return latest V12 contest context without backend identifiers.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
list_presetsGet Presets
List the available strategy presets (gpp_pro_pattern, gpp_sniper, gpp_balanced, gpp_volume, cash_grinder, gpp_contrarian, gpp_mass_entry) with their configurations. No auth required.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
list_slatesGet Slates
List available V12 slates for today. Returns slate IDs, game counts, and lock times.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
run_mlb_postmortemRun Mlb Postmortem
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**Example Response:**
```json
{
"status": "Status",
"generated_at": "Generated At",
"date": "Date",
"game_id": "Game Id",
"entries": 1,
"field_lineups": 1,
"training_rows": 1,
"missing_sources": [
"string"
],
"results": {},
"history_validation": {},
"field": {},
"diagnostics": {},
"simulator_feed": {},
"warnings": [
"string"
]
}
```
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
scout_fieldScout Field
VIP-only (owner order 8/16): opponent-scouting profiles for the small
single-entry band. The owner's $65 table runs the SAME regulars nightly;
this returns each regular's fingerprint — days seen, avg score,
chalkiness (overlap with field consensus), favorite pitchers/bats and
head-to-head vs the owner — built from harvested full fields
(brain/scout_profiles.json, refreshed by the local scouting pipeline;
packaged snapshot as fallback so the endpoint never 500s on a fresh
volume). Same fail-closed allowlist as the semaforo.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
slate_diffSlate Diff
Compute what changed since a previously-stored snapshot.
Body shape:
{
"slate_id": 32867,
"date": "2026-05-11",
"sport": "NBA",
"site": "FD",
"previous": {
"v": "v1",
"players": [{"id","name","status","salary","proj"}, ...],
"odds": [{"game","ou","spread","home_ml","away_ml"}, ...]
}
}
Returns a structured diff: which players changed status / salary /
projection, which games moved spread or O/U, which players were added
or removed from the pool. The thresholds for "changed":
- status: any non-empty difference (Q→OUT, ''→OUT, GTD→IN, etc.)
- salary: any integer delta
- projection: |delta| >= 0.5 fantasy points
- odds spread: |delta| >= 0.5
- odds ou: |delta| >= 0.5
- odds ml: |delta| >= 10 (American odds noise floor)
No auth required — read-only computation off in-memory current snapshot
plus the caller-supplied previous one.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
slate_healthSlate Health
Pre-flight diagnostic for a slate. Returns whether odds, projections,
matchup, and FD master-session are ready BEFORE the agent invokes
/v1/generate.
Either slate_id or date is required. When slate_id is given, the slate
metadata is also returned (games list, lock times). When only date is
given, the data-pillar checks still run but game coverage cannot be
computed (returned as null).
READING THE PROJECTION FRESHNESS (MLB especially): `stokastic.age_min` is the
age of the cached snapshot FILE, NOT a data-quality signal. For MLB the cache
is refreshed only twice a day, so mid-afternoon it routinely reads several
hours old AND THAT IS FINE — a user-facing generate fetches projections LIVE
(refresh_data=true), and `stokastic.generate_fetches_live=true` flags this.
A stale `age_min` with a loaded, populated pool is NOT "projections broken /
aces at 0 / no edge": probable pitchers are set days ahead (non-zero), and
only confirmed BATTING lineups firm up ~1-2h before lock. Do NOT treat a stale
cache age as a blocker or tell the user to wait/re-refresh — check the actual
pool (get_slate_players) for non-zero pitcher projections instead.
BLOCKERS vs WARNINGS: a blocker means generation will not work (slate closed) or the slate has a
PARTIAL odds gap (some games cached, some not). Nothing cached at all is a WARNING, not a blocker:
generate fetches odds/projections live. `data_store_ok=false` / `degraded=true` means the cache
store could not be read: degraded service, builds still fetch live, do not report the data as
unavailable and do not tell the user to wait.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
slate_refreshSlate Refresh
Re-fetch projections + odds + slate metadata for a date.
Writes to the configured store (Supabase in prod). Returns a summary
dict (date, slate_id, n_games, n_players, n_upserted, n_odds, backend).
Auth: requires X-API-Key OR X-Internal-Secret (cron use). This is a
write op that costs one Stokastic + one ESPN API call.
### Responses:
**200**: Successful Response (Success Response)
Content-Type: application/json
**422**: Validation Error
Content-Type: application/json
**Example Response:**
```json
{
"detail": [
{
"loc": [],
"msg": "Message",
"type": "Error Type",
"ctx": {}
}
]
}
``` | Not declared | Not declared | Not declared | Not declared |
Details
- Registry status
- Active
- Published
- Jun 17, 2026
- Updated
- Jun 17, 2026
- Website
- Not given
- Repository
- Not given
- Categories (suggested)
- AI modelsSuggested categories are assigned automatically from the registry text and may be wrong. Verified operators can correct them.
- GDPR
- Not declared