Start a project

Tool 124 of 194 · Databases

SQL Query Plan Explainer

Paste the output of EXPLAIN ANALYZE and see which step of the query takes the time, where the planner guessed wrong, and what to try first.

SQL Query Plan Explainer at a glanceIllustration: 1, EXPLAIN ANALYZE; 2, processed in your browser; 3, Plan tree.SQL Query Plan Explainer$ curl -X→ fetch()1EXPLAIN ANALYZE3Plan tree2In yourbrowser
1 EXPLAIN ANALYZE 2 processed on your device 3 Plan tree

SQL Query Plan Explainer

Your query plan

For real times, run EXPLAIN (ANALYZE, BUFFERS) your query; in PostgreSQL or EXPLAIN ANALYZE your query; in MySQL 8. ANALYZE runs the query, so use a copy of the data for writes.

    Plan tree

    Where the time goes

    NodeOwn timeShareRows est. → actualLoopsEstimate

    Own time per node

    01

    What it does

    Turns EXPLAIN and EXPLAIN ANALYZE output into a plan tree with each step's own time, estimate errors and suggestions to test.

    • PostgreSQL text and FORMAT JSON, with ANALYZE and BUFFERS
    • MySQL EXPLAIN FORMAT=TREE, EXPLAIN ANALYZE and FORMAT=JSON
    • Own (exclusive) time per node from per-loop times
    • Estimated against actual rows, with 10x misestimates flagged

    02

    Private by design

    Everything happens in your browser. Nothing you type, paste or upload is sent anywhere, and it keeps working offline once the page has loaded.

    03

    What you get

    A plan tree, own time per step and things to test, with a Copy and a Download button on every result.

    • SQL
    • PostgreSQL
    • MySQL
    • Performance

    Why it matters

    EXPLAIN ANALYZE tells you exactly how a query ran, but the output is dense: nested steps, costs, per-loop times that have to be multiplied out, and the one line that matters buried in the middle. The usual problems hide in it: a sequential scan that reads 100,000 rows to keep 1,000, a planner estimate that's off by 100 times, a sort that spilled to disk.

    This visualiser reads the plan, rebuilds its tree, and works out each step's own time by taking its children's time away from its own, allowing for loops. It compares estimated and actual rows at every step and flags the patterns that usually explain a slow query, with a suggestion for each: an index on the filtered columns, ANALYZE or extended statistics for bad estimates, more work_mem for spills. They're phrased as things to test, because only your data can confirm them. Unlike hosted plan visualisers, nothing is uploaded or kept.

    How it works

    1. InputEXPLAIN output from PostgreSQL or MySQL
    2. In your browserOwn time, loops and estimates per step
    3. OutputThe slow step, bad estimates and index ideas

    Where it fits in a designer's workflow

    1. Plan
    2. Design
    3. Build
    4. Test
    5. Launch
    Making a slow query fast without guessing.

    By the numbers

    Own time per step in the sample PostgreSQL planSeq Scan on orders: 161.12 ms (85.9%); Index Scan on order_items: 22.02 ms (11.7%); Nested Loop: 2.635 ms (1.4%); HashAggregate: 1.536 ms (0.8%); Sort: 0.108 ms (0.1%)Seq Scan on orders161.12 ms (85.9%)Index Scan on order_items22.02 ms (11.7%)Nested Loop2.635 ms (1.4%)HashAggregate1.536 ms (0.8%)Sort0.108 ms (0.1%)
    Worked out by this tool from its sample EXPLAIN ANALYZE output (total 187.512 ms). Own time is a step's actual time multiplied by its loops, minus its children's. One sequential scan takes 85.9% of the time, and the planner expected 12 rows from it but got 1,468; the tool raised 4 findings. Source: PostgreSQL: Using EXPLAIN; MySQL 8: EXPLAIN ANALYZE.
    Show the numbers as a table
    StepOwn time (ms)Share (%)Rows expectedRows actualLoops
    Seq Scan on orders161.1285.91214681
    Index Scan on order_items22.0211.79841468
    Nested Loop2.6351.4117458761
    HashAggregate1.5360.81001121
    Sort0.1080.11001121

    How to use it

    1. Run EXPLAIN (ANALYZE, BUFFERS) on your query in PostgreSQL, or EXPLAIN ANALYZE in MySQL 8.
    2. Paste the whole output.
    3. Read the summary and the slowest step, then the findings.
    4. Test the suggestions on a copy of the data, and compare the new plan.

    FAQ

    What's the difference between EXPLAIN and EXPLAIN ANALYZE?

    EXPLAIN shows the plan with the planner's estimates. EXPLAIN ANALYZE also runs the query and records real times and row counts, which is what you need to find the slow step. It really runs the query, so wrap writes in a transaction you roll back.

    Why is a node's own time different from its actual time?

    A node's actual time includes everything below it, and it's per loop. Own time is the node's total (time multiplied by loops) minus its children's totals, which is the time spent in that step alone.

    Why does a bad row estimate matter?

    The planner picks join types and orders from its estimates. If it expects 12 rows and gets 1,468, it may choose a nested loop that runs its inner side 1,468 times instead of one hash join. ANALYZE refreshes statistics; CREATE STATISTICS helps when columns are correlated.

    Will the suggested index definitely help?

    Not definitely. It's based on the columns the scan filters on, equality columns first. Create it on a copy of your data and check the new plan; also weigh the cost of maintaining it on writes.

    Is my plan uploaded?

    No. It's parsed in your browser and nothing is stored.

    Work with me

    Want a site that gets these right?

    I build fast, accessible websites and web apps that pass these checks from day one. Tell me about your project and I'll reply personally with honest next steps.

    All developer tools · Back to leej.uk