⚙ Automatic bet analysis — where it actually stands

Honest status · 2026-09-10 · what runs by itself, what never will

The headline: the lines automation is already built. It is switched off.

This was not a thing to propose — it exists. functions/bets/odds-fetch.js is a live Pages Function wired to The Odds API, with a 15-minute KV cache, per-month call accounting against the free tier, and a usage dashboard at /bets/api-usage/.

Tested today: it returns 503 api-key-missing. It has never had a key. One environment variable is the whole distance between "no automatic lines" and "automatic lines".

Update 2026-09-13: lines and finals without a key

Lines: gen-bet-lines.js reads ESPN's public game data (DraftKings, one book) for every NFL game in the next 8 days and feeds the hub. No key. The Odds API above would still add more books and history.

Finals: nfl-finals-to-ledger.js closes ledger rows when ESPN marks a game final. A logged pick is auto-graded; a game with no line becomes MISSED. It never invents a line.

VERIFIED 2026-09-13 20:21 ET: the first heartbeat commit (5d3b1974, github-actions) shows the job runs on GitHub, reaches ESPN (espn_ok: true), and can read the phone queue. The paragraph below is kept as the diagnosis that led to the heartbeat.

(Before verification) The game-night GitHub job (.github/workflows/nfl-finals.yml) was UNVERIFIED. It had not produced a single commit. The likely cause is a blind spot, not a crash: it only committed when it closed a game, and CC had already closed each one locally, so any run that did happen left no trace. The Actions run history is behind a GitHub login this machine does not have, so CC could not check. Since 2026-09-13 every CI run writes handoff-blocks/ci/nfl-finals-heartbeat.json (when it ran, whether ESPN answered) and commits it at least every 2 hours (6 until 2026-09-14, which let a whole game night pass unseen), or immediately if ESPN refused. That settles "does it run, and can GitHub's servers reach ESPN" at the first run.

Manual fallback, always works: node handoff-blocks/scripts/nfl-finals-to-ledger.js (add --dry-run to preview). If a phone line is still queued it holds the game rather than marking it MISSED; run node handoff-blocks/scripts/process-queue.js first.

To switch it on

  1. Register a free key at the-odds-api.com — the free tier is 500 calls a month.
  2. Set ODDS_API_KEY in Cloudflare Pages → Settings → Environment variables — the same place as ADMIN_INVITE_SECRET. Not in this repo: git history is permanent, and gated is not undoable.
  3. Redeploy. The usage page starts counting.

The budget already works out. The existing notes reckon roughly 12 calls per three hours of viewing one game, about 200 a month at typical use — comfortably inside 500. The cache is what makes that true, and it is already written.

What CC can do on its own

TaskStatus
Pull final scores and player stats after a gameYES — published facts, done for last night
Grade the analysis against the resultYES — the backtest on the NE@SEA page
Track placed bets and maintain the ledgerYES, once Sam says what he staked
Build and merge page structureYES
Verify schedules and matchupsYES — tonight's game was checked rather than assumed
Refresh a data feed on a runYES — the ADP feed already works this way; odds would too, with a key

What CC cannot do on its own, and saying so is the point

TaskWhy not
Forward-looking analysis — the read on a matchupNeeds live research: injury reports, beat coverage, line movement in the hours before kickoff. CC runs when Sam runs it, not continuously
Watch a line moveEven with the API key, CC has no schedule. The relay waits for a session — there is no always-on worker
Decide a betThat is Sam's, and it should stay Sam's
So "fully automatic pre-game analysis" is not a thing that exists here, and pretending otherwise would be the expensive kind of wrong. The realistic division is: CC does the data, the record and the structure · the planning chat does the forward read · Sam decides. The API key would move ONE thing from the second column to the first: current lines, on demand, without a person fetching them.

What last night proved about the analysis half

The one position the page argued for lost by 21.5 points. Both positions it declined to take were right. The MLB backtest already found that STRONG bets underperformed MEDIUM ones; this is a second sport saying the same thing.

Which is an argument about where automation is worth having. Automating the confident half — picks and reads — would industrialise the part with no demonstrated edge. Automating the record-keeping half industrialises the part that has actually been missing, and the ledger holding one tracked bet since May is the evidence for which of those matters.

Seven of the fifteen older game pages are unfilled skeletons. The constraint has never been the ability to generate analysis. It has been grading it afterwards.

Bets hub · Odds API usage · Last night, graded · The record
Written 2026-09-10. The 503 was tested today, not assumed.