Three bugs prevented game stats from recording: 1. broadcast_game_state had game_over processing (log_game_end + stats) inside the per-player loop — if all players disconnected before the loop ran, stats never processed. Moved to run once before the loop. 2. room.broadcast and broadcast_game_state iterated players.items() without snapshotting, causing RuntimeError when concurrent player disconnects mutated the dict. Fixed with list(). 3. stats_service.process_game_from_state passed avg_round_score to a CASE expression without a type hint, causing asyncpg to fail with "could not determine data type of parameter $6". Added ::integer casts. Also wrapped per-player send_json calls in try/except so a single disconnected player doesn't abort the broadcast to remaining players. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
37 KiB
37 KiB