refactor: deduplicate persistence, add upsert queries, throttle snake saves #4

Merged
ryan merged 3 commits from refactor/game-efficiency into main 2026-03-03 05:02:04 +00:00
Owner

Summary

  • Upsert queries — Replaced separate Create+Get+Update SQL with single UpsertGame and UpsertSnakeGame queries using INSERT ... ON CONFLICT DO UPDATE, cutting the per-save query count from 2-3 to 1
  • Deduplicated persistence — Extracted free functions (saveGame, loadGame, saveGamePlayer, etc.) replacing identical methods duplicated across Store and Instance receiver types in both game/ and snake/ packages
  • Throttled snake DB saves — Snake game loop now writes to DB every 2 seconds or on game over, instead of every tick (5-15 Hz). Removed per-tick saves during countdown phase entirely
  • Removed duplicate generateID — Snake package now imports game.GenerateID instead of having its own copy
  • Fixed double-lock — Combined two consecutive lock/unlock blocks in c4game chat handler into one
  • Updated for sqlc pointer types — All code now uses *string/*time.Time instead of sql.NullString/sql.NullTime, matching emit_pointers_for_null_types: true

Stats

14 files changed, 312 insertions, 488 deletions (net -176 lines)

## Summary - **Upsert queries** — Replaced separate Create+Get+Update SQL with single `UpsertGame` and `UpsertSnakeGame` queries using `INSERT ... ON CONFLICT DO UPDATE`, cutting the per-save query count from 2-3 to 1 - **Deduplicated persistence** — Extracted free functions (`saveGame`, `loadGame`, `saveGamePlayer`, etc.) replacing identical methods duplicated across Store and Instance receiver types in both `game/` and `snake/` packages - **Throttled snake DB saves** — Snake game loop now writes to DB every 2 seconds or on game over, instead of every tick (5-15 Hz). Removed per-tick saves during countdown phase entirely - **Removed duplicate `generateID`** — Snake package now imports `game.GenerateID` instead of having its own copy - **Fixed double-lock** — Combined two consecutive lock/unlock blocks in c4game chat handler into one - **Updated for sqlc pointer types** — All code now uses `*string`/`*time.Time` instead of `sql.NullString`/`sql.NullTime`, matching `emit_pointers_for_null_types: true` ## Stats 14 files changed, 312 insertions, 488 deletions (net -176 lines)
ryan added 1 commit 2026-03-03 02:56:53 +00:00
refactor: deduplicate persistence, add upsert queries, throttle snake saves
Some checks failed
CI / Deploy / test (pull_request) Failing after 15s
CI / Deploy / lint (pull_request) Failing after 23s
CI / Deploy / deploy (pull_request) Has been skipped
bc6488f063
- Replace Create+Get+Update with UpsertGame/UpsertSnakeGame queries
- Extract free functions (saveGame, loadGame, etc.) from duplicated
  receiver methods on Store and Instance types
- Remove duplicate generateID from snake package, reuse game.GenerateID
- Throttle snake game DB writes to every 2s instead of every tick
- Fix double-lock in c4game chat handler
- Update all code for sqlc pointer types (*string instead of sql.NullString)
ryan added 1 commit 2026-03-03 04:39:35 +00:00
ci: generate templ files before test and lint steps
All checks were successful
CI / Deploy / test (pull_request) Successful in 16s
CI / Deploy / lint (pull_request) Successful in 25s
CI / Deploy / deploy (pull_request) Has been skipped
cb5458c9fc
ryan added 1 commit 2026-03-03 04:51:21 +00:00
refactor: add save()/savePlayer() methods on game instances
All checks were successful
CI / Deploy / test (pull_request) Successful in 14s
CI / Deploy / lint (pull_request) Successful in 25s
CI / Deploy / deploy (pull_request) Has been skipped
9a20467438
Wrap free persistence functions in instance methods for cleaner call
sites (gi.save() instead of saveGame(gi.queries, gi.game)). Methods
log errors via zerolog before returning them.
ryan merged commit f47eb4cdf3 into main 2026-03-03 05:02:04 +00:00
Sign in to join this conversation.
No Reviewers
No Label
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: ryan/games#4