Runbook category
Query performance
Almost every "the database is slow" ticket is one query and one plan. These runbooks start from EXPLAIN output rather than from a timer: what the planner chose, what it expected, and what it actually got. The fixes range from an index to a work_mem change to leaving the plan alone because a sequential scan was right all along.
- Free
Slow query from a sequential scan on a large table
Same query, no code change, quietly slower every month as the table grows.
- Free
Replace deep OFFSET paging with keyset pagination
Page 1 is instant, page 10,000 crawls, and infinite scroll is your slowest endpoint.
- Pro
Tame a lossy bitmap heap scan
Row counts look sane, CPU does not — the plan quietly went lossy on you.
- Pro
Why your query ignores the index, and how to fix it
You built the index. EXPLAIN still says Seq Scan and nobody can say why.
- Pro
Speed up COUNT(*) on a large table
A dashboard polls count(*) and every refresh reads the entire table again.
- Pro
Fix bad row estimates with extended statistics
Estimate says 480 rows, reality is 10,000, and the join strategy goes with the guess.
- Pro
Why parallel query did not kick in
A big aggregate runs on one core while the rest of the box sits idle.
- Pro
Choose the right join: fix a nested loop on a misestimate
A join that returns a single row hashes two whole tables to find it.
- Pro
Control CTE materialization fences
Your WHERE clause runs after the WITH block has already spilled to disk.
- Pro
Refresh stale statistics that break query plans
Plans go wrong straight after a bulk load: estimated 1 row, actual 312.
- Pro
Replace an N+1 pattern with a LATERAL join
Latest-row-per-parent reads every child row, then throws nearly all of them away.
- Pro
Stop disk-spilled sorts by tuning work_mem
Sort Method says external merge Disk, and no row count explains the extra time.
- Pro
Cure HOT update degradation with fillfactor
Update-heavy table and its indexes keep growing while the row count stays flat.
- Pro
Diagnose detoasting overhead on wide rows
Identical plan, 100x slower the moment you select the big text column.
- Pro
Custom plan versus generic plan in prepared statements
The sixth run of an unchanged prepared statement is twenty times slower than the fifth.
- Pro
Reduce high planning time on complex queries
Execution is milliseconds, the request is not — it is all planning time.