Problem
recalculatePlayerAggregates only persists career_avg (plus practice/game avgs), but My Stats StatsOverviewCards reads career_obp, career_slg, and career_ops — fields that are never written.
Evidence
src/app/baseball/actions/stats.ts (lines 515-531): upserts career_avg, practice_avg, game_avg only
src/components/baseball/player-stats/StatsOverviewCards.tsx (lines 85-88): displays aggregates.career_obp/slg/ops
Why it matters
Players with CSV/practice upload data see AVG populated but OBP/SLG/OPS permanently show "---" in the overview cards, despite sufficient counting stats in baseball_player_stats.
Acceptance criteria
recalculatePlayerAggregates derives and stores career_obp, career_slg, career_ops from summed counting stats (standard formulas, null on zero denominators).
- My Stats overview cards show the computed slash line after upload.
- Unit test covers a multi-session aggregate with walks/SF/HBP.
Problem
recalculatePlayerAggregatesonly persistscareer_avg(plus practice/game avgs), but My StatsStatsOverviewCardsreadscareer_obp,career_slg, andcareer_ops— fields that are never written.Evidence
src/app/baseball/actions/stats.ts(lines 515-531): upsertscareer_avg,practice_avg,game_avgonlysrc/components/baseball/player-stats/StatsOverviewCards.tsx(lines 85-88): displaysaggregates.career_obp/slg/opsWhy it matters
Players with CSV/practice upload data see AVG populated but OBP/SLG/OPS permanently show "---" in the overview cards, despite sufficient counting stats in
baseball_player_stats.Acceptance criteria
recalculatePlayerAggregatesderives and storescareer_obp,career_slg,career_opsfrom summed counting stats (standard formulas, null on zero denominators).