Translate

sábado, 23 de mayo de 2026

Guía de EXPLAIN ANALYZE en MySQL: cómo leer el plan de ejecución de verdad


Cuando trabajamos con performance en MySQL, entender el plan de ejecución es fundamental.


EXPLAIN nos da una idea pero EXPLAIN ANALYZE nos dice la verdad.


Si hacemos: 

EXPLAIN ANALYZE SELECT ...


Ejecuta la query (Ojo! si la query demora tanto que no termina la ejecución, ya esta no podemos usarlo) y devuelve:

  • El plan de ejecución
  • Métricas reales de ejecución
  • Comparación entre estimaciones y realidad


Ejemplo típico:


-> Nested loop inner join  (cost=0.787 rows=1.25)

   (actual time=0.0644..0.0705 rows=1 loops=1)


    -> Index lookup on tabla1 ...

       (cost=...) (actual time=... rows=... loops=...)


    -> Index lookup on tabla2 ...

       (cost=...) (actual time=... rows=... loops=...)


Esto es un árbol de ejecución:

  • De arriba hacia abajo
  • Cada nodo es una operación


Conceptos clave (los más importantes):

cost


(cost=0.787 rows=1.25)


Es una estimación del optimizador.

Incluye:

  • I/O esperado
  • CPU estimado
  • Lecturas de índice / tabla


⚠️ Importante:

❌ No es tiempo real

❌ No está en milisegundos

✔️ Solo sirve para comparar planes


rows (estimado)

rows=1.25

Cantidad estimada de filas.


Puede ser decimal porque:

  • Es un promedio estadístico
  • Ej: 1.25 filas por iteración


actual time


actual time=0.0644..0.0705


Tiempo real en milisegundos:

  • Primer valor → tiempo hasta la primera fila
  • Segundo valor → tiempo hasta la última fila


actual rows

rows=1

Filas reales procesadas.


loops

loops=1


Cuántas veces se ejecutó ese paso.


Relación clave

filas totales ≈ rows × loops


Tipos de operaciones (nodos del plan)


Nested Loop Join

MySQL usa principalmente este tipo de join.


Funcionamiento:

  1. Toma una fila de la tabla A
  2. Busca coincidencias en tabla B
  3. Repite


Index Lookup

Index lookup on tabla using index_name


Búsqueda usando índice:

✔️ Rápido

✔️ Ideal


Covering Index Lookup

El índice tiene todas las columnas necesarias.


✔️ No accede a la tabla

✔️ Más eficiente


Table Scan

Table scan on tabla


Escaneo completo.

❌ Costoso

❌ Señal de posible problema


Range Scan

Range scan on index


Usa índice, pero en un rango:

WHERE fecha BETWEEN ...


✔️ Bueno, pero no tan óptimo como lookup exacto


Filter

Filter: (condición)


Filtra filas después de leerlas.


⚠️ Si aparece mucho → puede faltar índice


Sort

Ordenamiento (`ORDER BY`)

❌ Puede usar memoria o disco


Temporary Table

Using temporary


MySQL crea tabla intermedia y puede impactar performance


Cómo leer un plan (estrategia real)


Paso 1: leer de abajo hacia arriba

  • Primero las hojas (tablas base)
  • Luego los joins


Paso 2: comparar estimado vs real


rows=1000 vs actual rows=10


Mala estimación → posible mal plan


Paso 3: mirar loops

Detecta:

  • nested loops costosos
  • operaciones repetidas


Paso 4: identificar scans


Buscar:

Table scan


Candidato a optimización


Problemas comunes detectables

1. Mala estimación

2. Full table scan innecesario

3. Nested loops costosos

4. Filtros tardíos


Veamos un ejemplo:


-> Nested loop inner join  (rows=1.25)

   (actual rows=1 loops=1)


    -> Covering index lookup on autores

       (rows=1 actual rows=1)


    -> Index lookup on libros

       (rows=1.25 actual rows=1)


Interpretación:

1. Encuentra 1 autor

2. Estima 1.25 libros por autor

3. Realmente hay 1


✔️ Plan correcto

✔️ Estimación aceptable


EXPLAIN ANALYZE es la herramienta más poderosa para entender performance en MySQL.


Pero requiere cambiar la mentalidad:

  • No mirar solo el resultado
  • Entender cómo MySQL llega a él



No hay comentarios.:

Publicar un comentario