Session 23: All-day intelligence layer — schedule, game lines, streaks, hot lists, stat filtering, ParlayAPI dead (1567 tests)

This commit is contained in:
Kev
2026-06-12 11:16:58 -04:00
parent 6ab49d4c37
commit 0538205fab
32 changed files with 2276 additions and 2 deletions
+56
View File
@@ -0,0 +1,56 @@
/**
* /api/schedule/:sport (Session 23)
*
* Returns today's game schedule from cached/free ESPN data. NO odds-api
* credits burned. The PM2 pollers warm this cache every 60s; on a miss
* the schedule service self-heals by fetching the free ESPN scoreboard.
*
* Each game carries two boolean flags read from OTHER caches (no fetch):
* hasOdds — odds-api player props exist for this slate
* hasGameLines — Tank01 game-level lines exist for this slate
*
* Response shape:
* {
* sport: 'nba',
* date: '2026-06-12',
* games: [ { id, homeTeam, awayTeam, gameTime, status, score,
* venue, broadcast, hasOdds, hasGameLines } ],
* source: 'espn',
* }
*/
const express = require('express');
const scheduleService = require('../services/scheduleService');
const { SPORT_CONFIG } = require('../config/sports');
const router = express.Router();
const MISSION_HEADER = { 'X-VYNDR-Mission': 'The slate is never empty' };
router.get('/:sport', async (req, res) => {
const sport = String(req.params.sport || '').toLowerCase();
const date = req.query.date || scheduleService.todayET();
if (!SPORT_CONFIG[sport]) {
return res.status(404).set(MISSION_HEADER).json({ error: `Unknown sport: ${sport}` });
}
try {
const raw = await scheduleService.getSchedule(sport, date);
// null → unsupported sport (already guarded above); treat defensively.
const games = await scheduleService.enrichFlags(sport, date, raw || []);
return res.set(MISSION_HEADER).json({
sport,
date,
games,
source: 'espn',
});
} catch (err) {
console.error(`[schedule/${sport}]`, err.message);
// Even on error we return an empty slate, not a 5xx — the platform
// is NEVER down. Other layers (game lines, props) keep it alive.
return res.set(MISSION_HEADER).json({ sport, date, games: [], source: 'espn' });
}
});
module.exports = router;