Inspect MySQL EXPLAIN plans and access paths

Paste a plan already obtained from MySQL: FORMAT=JSON, an EXPLAIN ANALYZE tree or copied console table output. The page lists the access type, selected key and estimated rows of every table, and flags full scans, temporary tables and filesort. Nothing is sent to a database and no statement is executed.

Runs locally in your browser
This tool processes all data locally in your browser.
MySQL EXPLAIN outputPaste EXPLAIN FORMAT=JSON, an EXPLAIN ANALYZE tree, a tab-separated result, or MySQL console table output.
JSON, table or tree inputEstimates need production contextNo database connection

This is a read-only plan review. It never runs a query or sends SQL to MySQL.

Access rows
No access rows to display yet.

How to read a MySQL plan from EXPLAIN output

Paste a plan you already have from MySQL: the FORMAT=JSON output, an EXPLAIN ANALYZE tree or the console table from the mysql client. The page lists every table it can find with its access type, selected key and estimated rows, and flags full table scans, temporary tables and filesort signals. It all runs in the browser; no statement is executed and nothing is sent to a database.

The analyzer reads the three shapes MySQL itself prints and does not invent numbers: when a plan carries no row estimate the column shows — instead of 0. Estimates come from the server's statistics, so treat them as the planner's guess, not as a measurement of the query.

  1. Run EXPLAIN in MySQL and copy the whole result: EXPLAIN FORMAT=JSON for the JSON plan, EXPLAIN ANALYZE or EXPLAIN FORMAT=TREE for the tree, or the plain EXPLAIN table from the console.
  2. Paste it into the field and press Analyze locally. Load example fills the field with a two-table JSON plan that keeps a subquery inside the table object.
  3. Read the five counters first: access rows, estimated rows, full scans, keyed access and index scans.
  4. Work through the findings: ALL access, a full index scan, a temporary table, filesort and intermediate results are each named with the table they belong to.
  5. Check the table below for the selected key and the extra column (possible keys, join buffer, attached condition), then press Copy to take the report into a ticket before you change an index.

What the analyzer reports, and what it cannot

Rows, keys and what the counters mean

Access rows counts the table entries the analyzer found in the plan, not the rows the query touches; one entry is one line in the table below. Estimated rows adds up the rows_examined_per_scan (or rows) values it can read and shows — when none of the entries carries a number. Full scans counts access type ALL, index scans counts INDEX, and keyed access counts the entries where a key was actually selected.

The table keeps the plan's own wording: access type, selected key, filtered, and an extra column that names possible keys when no key was chosen, a join buffer or an attached condition. possible_keys is a candidate list, not a chosen index, so it is never printed in the selected-key column.

JSON, tree and console output

MySQL 8 keeps subqueries and materialized views inside the table object (attached_subqueries, materialized_from_subquery). The analyzer descends into them, so an inner table appears as its own row, and a self-join that scans the same table twice is reported twice instead of being collapsed.

Tree output from EXPLAIN ANALYZE is read line by line (Table scan, Index scan, Index range scan, Index lookup …), and when the tree carries actual rows the page prints them next to the estimate. Console output is read as tab-separated or pipe-delimited columns, so the mysql client table can be pasted as it is. Plans with more than 250 access rows are cut off after the 250th line and the report says so.

Limits: one plan, one moment

The page cannot connect to MySQL: it cannot run the query, cannot see your schema or statistics, and cannot tell whether the server would still choose this plan. A plan taken without ANALYZE carries estimates only, and a plan from another MySQL version may name keys or access types this page does not know.

Nothing is cached between runs: a new analysis replaces the previous counters, findings, table and report, and text that is not an EXPLAIN plan clears the panels instead of leaving an old report that Copy could hand over. The report itself repeats the format, the counters and every finding, so the notes travel with the numbers.

Recent tools: