Rendimiento web: la regla de los 100 ms y la nueva métrica INP
Google cambió las reglas con INP (Interacción con Next Paint). optimización para React Hydration y Edge Caching.
La velocidad no es algo “bueno de tener”. La velocidad es la única característica que experimenta todo usuario. Amazon descubrió que cada 100 ms de latencia les costaba un 1% en ventas. Walmart descubrió que mejorar el tiempo de carga en 1 segundo aumentaba las conversiones en un 2 %. En 2025, el listón será más alto. Core Web Vitals de Google ha cambiado su enfoque de LCP (carga) a INP (interacción con la siguiente pintura). Ya no basta con cargar rápido. Debes responder rápido.
Por qué Maison Code habla de esto
En Maison Code Paris, actuamos como la conciencia arquitectónica de nuestros clientes. A menudo heredamos stacks “modernos” construidos sin una comprensión fundamental de la escala.
Discutimos este tema porque representa un punto de inflexión crítico en la madurez de la ingeniería. Implementarlo correctamente diferencia un MVP frágil de una plataforma resistente de nivel empresarial.
Por qué Maison Code se obsesiona con más de 100 ms
La velocidad es nuestra marca. No nos limitamos a “optimizar imágenes”. Rediseñamos todo el proceso de entrega.
- Infraestructura: Implementamos en el borde (Vercel/Cloudflare) para estar dentro de los 50 ms del usuario.
- Hidratación: Usamos hidratación selectiva para hacer que el “Botón Comprar” sea interactivo incluso antes de que se cargue el pie de página.
- Resultado: Nuestros clientes aprueban consistentemente Core Web Vitals, lo que lleva a una mejora de SEO medida de 15-20 %. Tratamos los presupuestos de desempeño como presupuestos financieros. Gastar demasiado no es una opción.
La API de reglas de especulación
La solicitud de red más rápida es la que no realiza. En 2025, utilizaremos la API de reglas de especulación para renderizar previamente las páginas antes de que el usuario haga clic. Esto no es una “captación previa” estándar. Chrome literalmente construye el DOM en una pestaña en segundo plano. Cuando el usuario hace clic, la transición es de 0 ms. Instante.
<!-- Inyectando reglas de especulación -->
<script tipo="reglas de especulación">
{
"prerenderizar": [
{
"fuente": "documento",
"dónde": {
"y": [
{ "href_matches": "/productos/*" },
{ "selector_matches": "a:hover" }
]
}
}
]
}
</script>
Seguridad y uso de datos
Una preocupación con la especulación es el uso de datos. Si renderizamos previamente 10 páginas y el usuario visita 0, desperdiciamos ancho de banda. El navegador es inteligente. Sólo especula si:
- El usuario está en Wi-Fi (no en modo de ahorro de datos).
- El dispositivo tiene suficiente memoria. Sin embargo, para un sitio de comercio electrónico, la “próxima acción” es extremadamente predecible. En una PDP (página de detalles del producto), la siguiente acción es “Agregar al carrito” o “Volver a la colección”. Especular sobre estas dos rutas produce una tasa de acierto del 90%.
INP: ¿El asesino de React?
INP mide el tiempo desde “Hacer clic” hasta “Pintar”. La hidratación de React es el enemigo de INP. Si un usuario hace clic en “Agregar al carrito” mientras React hidrata el pie de página, el hilo principal se bloquea. El botón ignora el clic. La puntuación INP llega a 400 ms (pobre). Google penaliza tu SEO.
Optimización de INP en Headless
- Hidratación Selectiva: Hidrata únicamente los componentes visibles. (Consulte Diseño atómico para el aislamiento de componentes).
- Web Workers: traslade la lógica pesada (Analytics, GTM) a un Web Worker a través de Partytown.
- API de transición: utilice
useTransitionpara marcar actualizaciones no urgentes.
// Implementación de transición de uso de React 19
importar {useTransition} desde 'reaccionar';
función AddToCart({ id }) {
const [está Pendiente, iniciarTransición] = useTransition();
const handleClick = () => {
// Urgente: actualizar la interfaz de usuario inmediatamente
setOptimisticCartCount(c => c + 1);
// No urgente: solicitud de red/actualización de estado
iniciarTransición(() => {
addToCart(identificación);
});
};
regresar (
<botón onClick={handleClick} deshabilitado={está Pendiente}>
{¿Está pendiente? 'Agregando...' : 'Agregar a la bolsa'}
</botón>
);
}
The Edge: La geografía importa
Si su servidor está en Virginia (us-east-1) y su cliente está en París, la velocidad de la luz impone una penalización de 100 ms. No se puede vencer a la física. Debes mover el cálculo. Edge Rendering (Oxygen/Vercel) ejecuta la lógica SSR en un centro de datos más cercano al usuario.
Estancado mientras se revalida (SWR)
No queremos llegar al origen de cada solicitud. Usamos la estrategia de caché SWR, un beneficio principal de la Arquitectura sin cabeza.
- El usuario A visita
/productos/zapato. - Edge ofrece la versión obsoleta (instantánea).
- Edge recupera la versión nueva en segundo plano.
- El usuario B obtiene la versión nueva.
En encabezados Remix/Hydrogen:
exportar encabezados de función() {
devolver {
'Control de caché': 'público, edad máxima = 60, s-maxage = 3600, obsoleto mientras se revalida = 86400',
};
}
Optimización de imagen: AVIF es el rey
Olvídese de WebP. AVIF es el estándar.
Es un 30% más pequeño que WebP y admite gamas de colores HDR (esencial para la moda).
La CDN de Shopify admite el formato automático AVIF.
Fuerza siempre format=auto en tu cargador de imágenes.
La estrategia “LQIP”
Marcadores de posición de imágenes de baja calidad. Mientras se carga la imagen de alta resolución, muestra una versión borrosa de 10 píxeles. Esto evita el “Layout Shift” (CLS) y da la percepción de velocidad. Generamos LQIP en el momento de la compilación o mediante una función sin servidor.
Guiones de terceros: El asesino silencioso
A las agencias les encanta instalar scripts. Hotjar, Klaviyo, Yotpo, Facebook Pixel, TikTok Pixel, Snap Pixel. Cada uno consume 50 ms de tiempo del hilo principal. Total = bloqueo de 300 ms.
El problema con “Async”
Los desarrolladores piensan que “Async” significa “Sin bloqueo”. Significa “búsqueda sin bloqueo”. Pero la Ejecución está bloqueando. Cuando se ejecuta Facebook Pixel, congela el hilo principal para eliminar el DOM.
Solución: GTM del lado del servidor
Mueva los píxeles al servidor.
- El navegador envía UN evento a su servidor (por ejemplo,
POST /api/events). - Su servidor (GTM Server Container) lo recibe.
- Su servidor lo distribuye en Facebook, TikTok y Google Ads. Cero impacto del lado del cliente. Bonificación: omite los AdBlockers porque la solicitud va a su propio dominio.
Solución: Partytown
Si DEBE ejecutar scripts del lado del cliente (como Hotjar, que necesita DOM), ejecútelos en un Web Worker. Partytown es una biblioteca que transfiere mutaciones DOM de un trabajador al hilo principal. Crea una zona de pruebas donde se pueden ejecutar scripts pesados de terceros sin congelar la interfaz de usuario.
<script type="text/partytown" src="https://connect.facebook.net/en_US/fbevents.js"></script>
Estrategias de carga de fuentes
La tipografía es sorprendentemente pesada. Un archivo de fuente personalizado (WOFF2) pesa ~50 kb. Si bloquea la renderización hasta que se carga la fuente (FOIT - Flash of Invisible Text), el usuario se queda mirando una pantalla en blanco. Si muestra una fuente alternativa (FOUT - Flash of Unstyled Text), el diseño cambia.
La pila de carga de fuentes perfecta
- Subconjunto: Incluye solo los caracteres que necesitas (Latin-1).
- Precarga: Utilice
<link rel="preload">para la fuente crítica (Encabezado). - Intercambiar: utilice
font-display: swap. Muestre el texto inmediatamente en Helvetica y luego cambie a su fuente. - Ajuste de tamaño: use CSS
size-adjustpara hacer que la fuente alternativa ocupe exactamente el mismo espacio que la fuente personalizada. Esto elimina el cambio de diseño.
@fuente-cara {
familia de fuentes: 'Bodoni Fallback';
origen: local('Times New Roman');
anulación de ascenso: 90%;
anulación de descenso: 20%;
ajuste de tamaño: 140%;
}
RON vs datos de laboratorio
Lighthouse (Lab Data) es una simulación. Se supone un Motorola G4 en red 3G. RUM (Monitoreo de Usuario Real) es una realidad. Mide lo que experimentan los usuarios reales. Es posible que tenga una puntuación de 100 en Lighthouse, pero si sus usuarios reales usan iPhones antiguos en el metro, sus datos de RUM mostrarán 3s LCP. Integramos Vercel Analytics o Datadog RUM para rastrear el p75 (percentil 75) de experiencias reales. Si tu p75 es verde, estás bien. Si tu Lighthouse es 100 pero p75 es rojo, estás fallando.
Conclusión
El rendimiento es una cultura de ingeniería. Debes tener un Presupuesto de rendimiento. “Si este PR agrega 10 kb al paquete, se debe eliminar algo más”. Cíñete a la regla de los 100 ms. Si tarda más de 100 ms, se siente roto. Los sitios de comercio electrónico más rápidos no sólo “se sienten” rápidos. Se sienten invisibles. La interfaz desaparece, quedando sólo el deseo y el producto.