Ir al contenido principal
Laravel, shipping fast.
Capítulo 9 · Rendimiento y optimización

Saber que la optimización funcionó

Julian Beaujardin

Esto cierra el círculo que abrió el capítulo. Mediste antes de tocar nada. Entrega el arreglo y mira después el mismo número.

Si no se movió, una de tres cosas es cierta: optimizaste lo que no era, el cuello de botella nunca estuvo donde creías, o el arreglo en realidad no se entregó. Más vale saber cualquiera de las tres que quedarse con «añadí caché, ahora debería ir más rápido».

Para las consultas, puedes fijar el resultado en un test para que no pueda empeorar sin que nadie lo note:

it('lists consumers in a fixed query count', function () {
    Consumer::factory()->count(20)->create();

    Sanctum::actingAs(
        Consumer::factory()->create(),
        ['consumers:manage'],
    );

    $this->expectsDatabaseQueryCount(3);

    $this->getJson('/api/consumers')->assertOk();
});

Veinte consumidores o dos mil, el recuento se queda en tres: una para contar las filas, una para traer la página y una para registrar la petición. El día que alguien añada una relación perezosa al Resource, este test se lo dice. (Documentación de Laravel: Database Testing.)

Resumen del capítulo 9

Antes de tocar nada:

  • Confirma la petición lenta en tus mediciones. No trabajes a partir de una sensación.
  • Identifica si el costo está en la base de datos, en una llamada externa o en el tamaño de la respuesta. Devuelve los campos que un consumidor usa, y ningún otro.

Consultas:

  • Agrupa en lotes o carga de forma anticipada cualquier consulta que fuera a ejecutarse una vez por fila de un bucle.
  • Activa shouldBeStrict() fuera de producción.
  • Acota el tamaño de página, por los dos lados, en cualquier endpoint donde lo elija un cliente. Usa cursorPaginate() cuando nadie necesite el total.
  • Cada índice corresponde a una cláusula WHERE real, en el orden de columnas por el que filtra la consulta.

Caché:

  • Cachea lo que es caro, normalmente las llamadas de red, no las búsquedas que ya son rápidas.
  • Cachea arrays planos, y construye los objetos después de la lectura.
  • Cada clave de caché incluye todo lo que haga que los datos sean distintos para llamantes distintos.
  • Cada escritura olvida la clave que invalida, por su nombre, donde ocurre la escritura, haya salido bien o no.

Esperar a un proveedor:

  • Dale a cada llamada saliente un timeout de conexión y un timeout total, y suma el peor caso contando los reintentos.
  • Deja de llamar a un proveedor que está caído. Un contador en el limitador basta.

Después de entregar:

  • Confirma que el número se movió. Si no se movió, averigua por qué antes de seguir.

No se pudo cargar el audio. Inténtalo de nuevo en un momento.