Skip to main content

Database Query Cost Analyzer

Paste a SQL query to detect common performance anti-patterns and get optimization suggestions.

Common Anti-Patterns

✗SELECT * — fetches all columns, prevents index-only scans
✗WHERE func(col) = ? — function on indexed column bypasses index
✗LIKE '%term' — leading wildcard = full scan
✗OR across different columns — often can't use index
✗NOT IN (subquery) — use NOT EXISTS instead
✗Implicit type conversion in WHERE clause
✗OFFSET with large values — scans all preceding rows
✗Correlated subquery in SELECT — runs once per row
Paste a query and click Analyze to detect issues.

Frequently Asked Questions

What makes a SQL query slow?▼

The main culprits: 1) Full table scans — no index on filtered columns. 2) N+1 queries — fetching related records one at a time in a loop. 3) SELECT * — fetching unnecessary columns, especially with large TEXT/BLOB columns. 4) Missing index on JOIN columns. 5) Functions on indexed columns (WHERE LOWER(email) = '...' bypasses the index). 6) LIKE '%term' — leading wildcard prevents index use.

How do I read EXPLAIN output?▼

Key fields: 'Seq Scan' = full table scan (bad for large tables). 'Index Scan' = uses index. 'Bitmap Heap Scan' = index + heap fetch. 'Hash Join' / 'Merge Join' = common for large joins. 'cost=X..Y' means estimated rows X to Y. 'rows=' is estimated row count. 'actual time=' (in EXPLAIN ANALYZE) shows real execution time. Look for high cost nodes and missing indexes.

What is an index scan vs index-only scan?▼

Index scan: PostgreSQL uses the index to find row locations, then fetches the actual heap (table) rows to get full column data. Index-only scan: all needed columns are in the index itself — no heap fetch needed. Much faster. To get index-only scans, include all SELECT columns in the index using INCLUDE (PostgreSQL 11+) or a covering index.

What is the N+1 query problem?▼

N+1 happens when you fetch a list of N items, then for each item run 1 more query to fetch related data. Example: fetch 100 users (1 query), then for each user fetch their posts (100 queries) = 101 total queries. Fix: use a JOIN to fetch both in one query, or use eager loading (with the ORM) with IN clauses.

Share this tool: X / Twitter LinkedIn
✓ 60,000+ developers use DevPlaybook ★★★★★ 4.8 / 5 on Gumroad ✓ MIT licensed · Instant download ✓ No login required

Related Products

on Gumroad

You Might Also Need

More Free Tools

Enjoying this tool? Get more like it.

Weekly developer tool guides, productivity playbooks & AI tricks. Free. No spam.

DevPlaybook Pro 7 days free

Unlock AI-Powered Dev Tools

  • ⚡ AI Code Review, Doc Generator & SQL Builder
  • ⚡ All premium templates & early access
  • ⚡ Member discounts on Gumroad products
Start Free Trial →

$9/mo after trial · Cancel anytime

Want the full toolkit?

Get DevPlaybook Pro

Every template, guide, boilerplate, and automation script in one bundle. 13 premium products — grab them all at once and save big.

$79
$241 separately Save $162 (67% off)
Get DevPlaybook Pro — $79 →

MIT licensed · Instant download · No subscription

See what's included → Browse all deals →