diff --git a/app/routers_v2/season_stats.py b/app/routers_v2/season_stats.py index 90c0b8e..eb87e59 100644 --- a/app/routers_v2/season_stats.py +++ b/app/routers_v2/season_stats.py @@ -4,11 +4,13 @@ Covers WP-13 (Post-Game Callback Integration): POST /api/v2/season-stats/update-game/{game_id} Delegates to app.services.season_stats.update_season_stats() which -aggregates StratPlay and Decision rows for a completed game and -performs an additive upsert into player_season_stats. +recomputes full-season stats from all StratPlay and Decision rows for +every player who appeared in the game, then writes those totals into +batting_season_stats and pitching_season_stats. Idempotency is enforced by the service layer: re-delivery of the same game_id returns {"updated": 0, "skipped": true} without modifying stats. +Pass force=true to bypass the idempotency guard and force recalculation. """ import logging @@ -29,10 +31,10 @@ async def update_game_season_stats( """Recalculate season stats from all StratPlay and Decision rows for a game. Calls update_season_stats(game_id, force=force) from the service layer which: - - Aggregates all StratPlay rows by (player_id, team_id, season) - - Merges Decision rows into pitching groups - - Performs an additive ON CONFLICT upsert into player_season_stats - - Guards against double-counting via the last_game FK check + - Recomputes full-season totals from all StratPlay rows for each player + - Aggregates Decision rows for pitching win/loss/save/hold stats + - Writes totals into batting_season_stats and pitching_season_stats + - Guards against redundant work via the ProcessedGame ledger Query params: - force: if true, bypasses the idempotency guard and reprocesses a diff --git a/app/services/evolution_evaluator.py b/app/services/evolution_evaluator.py index bb72136..ee36b3b 100644 --- a/app/services/evolution_evaluator.py +++ b/app/services/evolution_evaluator.py @@ -54,9 +54,9 @@ def evaluate_card( ) -> dict: """Force-recalculate a card's evolution tier from career stats. - Sums all player_season_stats rows for (player_id, team_id) across all - seasons, then delegates formula computation and tier classification to the - formula engine. The result is written back to evolution_card_state and + Sums all BattingSeasonStats or PitchingSeasonStats rows (based on + card_type) for (player_id, team_id) across all seasons, then delegates + formula computation and tier classification to the formula engine. The result is written back to evolution_card_state and returned as a dict. current_tier never decreases (no regression):