Cómo la mejora del INP de Fotocasa contribuyó a un crecimiento del 27% en las métricas clave

Publicado: 14 de octubre de 2025

La métrica Interaction to Next Paint (INP) es una métrica de Métricas web esenciales fundamental para medir la capacidad de respuesta. En Fotocasa, Google Search Console destacó una cantidad significativa de páginas que cambiaron a "Necesita mejoras" y "Deficiente" cuando INP reemplazó el Retraso en la primera entrada (FID) en 2024. En este caso de éxito, se describen las herramientas y estrategias que se emplearon para diagnosticar y resolver estos problemas, lo que, en última instancia, mejoró el INP en un margen considerable.

Dónde comenzó el equipo de Fotocasa

Antes del cambio del FID al INP, casi todas las páginas en computadoras y dispositivos móviles estaban dentro del umbral de "Rápidas", lo que significa que todas las Métricas web esenciales en ese momento (LCP, CLS y FID) tenían un buen rendimiento. Sin embargo, después del cambio al INP, casi todas las páginas cambiaron a "Necesita mejorar" y algunas incluso a "Deficiente", ya que los valores del INP superaron constantemente los 200 milisegundos para la mayoría de las interacciones del usuario.

Google Search Console muestra la distribución de las URLs de Fotocasa en computadoras, con muchas páginas que pasaron de "Buena" a "Necesita mejorar" después de que el INP se convirtió en una Core Web Vital.
Fig. 1. Google Search Console: Distribución de URLs de Fotocasa en computadoras de escritorio: Cuando entra en vigencia el INP, muchas URLs que antes se clasificaban como "buenas" pasan a la categoría "Necesita mejorar".

Este cambio hizo que el equipo de Fotocasa se diera cuenta de que estaba pasando por alto un aspecto crucial de la experiencia del usuario. Si bien el FID solo medía la demora de la primera interacción, el INP evalúa la capacidad de respuesta de todas las interacciones, teniendo en cuenta las demoras en el procesamiento y la presentación de la entrada. Esta medición más amplia es un proxy mucho mejor para la verdadera interactividad (como afirma Google) y destaca las oportunidades perdidas.

Si bien Google Search Console proporciona datos de rendimiento de campo, no ofrece estadísticas en tiempo real. Sus datos se agregan en un período de 28 días, lo que dificulta determinar con exactitud qué interacciones causaban problemas en el momento.

Se necesitaba una forma de hacer un seguimiento del INP en tiempo real para identificar las interacciones más lentas y las que los usuarios usaban con mayor frecuencia, y reproducirlas de manera confiable en los entornos de desarrollo del equipo. También era importante comprender el impacto de los cambios realizados, no solo qué correcciones ayudaron, sino también qué ajustes empeoraron las cosas sin querer.

Por estos motivos, se usó un conjunto de herramientas para ayudar a diagnosticar y resolver los problemas. Los más importantes fueron los siguientes:

  • Herramientas para desarrolladores de Google Chrome, específicamente la pestaña Rendimiento
  • Un sistema de RUM (supervisión de usuarios reales) personalizado que el equipo de Fotocasa creó en Datadog con la biblioteca de web-vitals.
  • Herramientas para desarrolladores de React

Herramientas para diagnosticar el problema

Para diagnosticar y depurar los problemas de rendimiento del INP, se usaron las siguientes herramientas.

Herramientas para desarrolladores de Google Chrome

Una excelente manera de detectar y reproducir problemas relacionados con las Métricas web esenciales en una aplicación web es usar la pestaña Rendimiento en las Herramientas para desarrolladores de Google Chrome. La pestaña Rendimiento mide automáticamente las métricas de Métricas web esenciales y proporciona comentarios instantáneos sobre las métricas de cambio de diseño, interactividad y carga. En general, es coherente con la forma en que estas métricas se informan a otras herramientas de Google.

La pestaña Rendimiento en las Herramientas para desarrolladores de Google Chrome, que muestra una línea de tiempo con varias métricas de rendimiento, como LCP, FID y CLS, junto con la actividad de la CPU y la red.
Fig. 2. La pestaña Rendimiento en las Herramientas para desarrolladores de Google Chrome.

Para identificar y resolver los problemas relacionados con el INP, el equipo de Fotocasa suele comenzar por limitar la CPU para simular el rendimiento de los dispositivos de gama media y baja. Esto permitió que el equipo de Fotocasa observara cómo se comporta la página en condiciones más restringidas. Luego, se grabó la sesión con el generador de perfiles y se analizaron cuidadosamente los registros, enfocándose en la interacción del usuario para identificar los problemas de rendimiento.

La pestaña Rendimiento en las Herramientas para desarrolladores de Google Chrome muestra el menú desplegable de ralentización de la CPU con opciones como "Ralentización de 4 veces" y "Ralentización de 6 veces".
Fig. 3. La pestaña Rendimiento en las Herramientas para desarrolladores de Google Chrome que muestra el menú desplegable de ralentización de la CPU.

Cuando identificas cuellos de botella, es especialmente útil examinar las partes secundarias del INP y las tareas que el navegador realiza en cada una de ellas. Por ejemplo, en la siguiente imagen, se puede ver que el INP es bastante alto debido a dos nuevos cálculos de diseño causados por cambios de diseño en el cuerpo del documento.

La pestaña Rendimiento en las Herramientas para desarrolladores de Google Chrome muestra una tarea larga en el generador de perfiles, con detalles que indican que dos recálculos de estilo causan un INP alto.
Fig. 4. La pestaña Rendimiento en las Herramientas para desarrolladores de Google Chrome, que muestra el generador de perfiles completado.

Fotocasa configuró un sistema para hacer un seguimiento del INP y otras métricas de las Métricas web esenciales, lo que garantiza que cualquier problema de rendimiento se identifique y aborde rápidamente. Cuando una métrica supera un umbral específico (según los rangos definidos por Google), se registra la atribución para que se pueda analizar y resolver el problema.

Para ese sistema, se usó la biblioteca web-vitals para capturar estas métricas de usuarios reales de una manera que coincida con precisión con la forma en que Chrome las mide y las informa a otras herramientas de Google (como el Informe sobre la experiencia del usuario en Chrome, PageSpeed Insights, el Informe de velocidad de Search Console y otros).

Para obtener una vista integral y un seguimiento centralizado, Fotocasa usó Datadog para recopilar y visualizar los datos, lo que permitió al equipo tomar decisiones fundamentadas basadas en datos. Las métricas personalizadas mantienen la rentabilidad y permiten hacer un mejor seguimiento de casi todos los usuarios en el sitio web de Fotocasa.

El panel de Datadog de Fotocasa muestra varias métricas de rendimiento, incluidas INP, LCP y CLS, a lo largo del tiempo.
Fig. 5. Panel de rendimiento de RUM de Fotocasa Datadog.
Panel de Datadog que muestra gráficos de las métricas de retraso de entrada, duración del procesamiento y retraso de presentación.
Fig. 6. Métricas de retraso de entrada, duración del procesamiento y retraso de presentación.

Este sistema permite que el equipo de Fotocase supervise rápidamente si sus modificaciones afectan las métricas o si se producen alteraciones imprevistas que podrían comprometerlas. Luego, la métrica del INP se puede analizar en partes, como la demora de entrada, la duración del procesamiento y la demora de presentación, para identificar con precisión qué parte de la interacción es la principal responsable de los tiempos de interacción prolongados.

Un gráfico de Datadog que muestra un aumento repentino en los valores del INP, lo que indica una anomalía.
Fig 7. Se detectó una anomalía del INP en el panel.
Una alarma de supervisión en Datadog que muestra una anomalía del INP detectada.
Fig. 8. Se detectó una anomalía del INP en la alarma del monitor.

Cuando detectó anomalías, como la que se ilustra en las figuras 7 y 8, Fotocasa respondió de inmediato y usó OpenSearch, otra herramienta que ayudó a identificar dónde podría estar ocurriendo la alteración. Los datos proporcionados por la biblioteca de web-vitals ayudaron a identificar el objetivo (el elemento DOM potencialmente responsable de un valor de métrica elevado) y permiten que el equipo se concentre más en solucionar el problema.

Panel de OpenSearch que muestra datos de la biblioteca web-vitals, que se usa para identificar qué elementos del DOM afectan la métrica del INP.
Fig. 9. Panel de OpenSearch para depurar qué objetivo afecta la métrica del INP.

Además, se pueden definir varios filtros, como el tipo de página, el dispositivo o el estado de carga, para optimizar las situaciones y comprender con mayor precisión cómo se ve afectado el INP.

Herramientas para desarrolladores de React

Se usaron las Herramientas para desarrolladores de React para mejorar las capacidades de depuración de Fotocasa, lo que proporciona una función potente que te permite destacar visualmente los componentes que se volvieron a renderizar.

Para habilitar esta función, navega a la pestaña Profiler. Desde allí, haz clic en el engranaje que se encuentra en el lado derecho de la barra superior, ve a la pestaña General y marca la casilla de verificación Highlight updates when components render. Con esta opción activada, los componentes se destacan cuando se vuelven a renderizar, lo que proporciona una representación visual dinámica.

El panel de configuración en las Herramientas para desarrolladores de React, con la casilla de verificación "Highlight updates when components render" marcada.
Fig. 10. Configuración del generador de perfiles de las Herramientas para desarrolladores de React.

Cómo averiguar la causa de una nueva renderización

Una vez que se identifica un componente que se volvió a renderizar, la siguiente pregunta es "¿por qué sucedió?". React DevTools responde esto con una sugerencia útil en la vista de gráfico de llamas.

Para acceder a esta información, graba una sesión del generador de perfiles. Si analizas el resultado del generador de perfiles, encontrarás información útil:

  • En la esquina superior derecha, se muestra la cantidad de confirmaciones de React.
  • El gráfico de llamas representa visualmente el árbol de componentes, y el color gris indica los componentes que no se volvieron a renderizar. Cada barra representa un momento en el que cambió el árbol de componentes de React y en el que se confirmó un cambio correspondiente en el DOM.
  • Si colocas el cursor sobre cada componente del gráfico de llamas, se mostrará el motivo de su nuevo renderizado en el subtítulo "¿Por qué se renderizó?".

Entre los motivos por los que se vuelve a renderizar un componente, se incluyen los siguientes:

  • Es la primera vez que se renderizó el componente.
  • Cambió el contexto
  • Se cambiaron los hooks
  • Cambiaron las propiedades
  • El Estado ha cambiado
  • El componente principal renderizado
El generador de perfiles de React Developer Tools muestra un gráfico de llamas, con una información sobre herramientas abierta en un componente que explica que se volvió a renderizar porque "Cambiaron los Hooks".
Fig. 11. El panel de renderización en el generador de perfiles de las Herramientas para desarrolladores de React.

Cómo averiguar el tiempo de procesamiento

Los colores del gráfico de llamas transmiten información significativa. Los colores, como los distintos tonos de azul, indican que un componente requirió un tiempo de renderización relativamente corto en comparación con otros componentes. Por el contrario, los colores como el naranja y el rojo indican que un componente tardó más tiempo en renderizarse.

El generador de perfiles de React Developer Tools muestra un gráfico de llamas en el que los colores indican el tiempo de renderización, con tonos de azul que representan tiempos más cortos y tonos de naranja o rojo que representan tiempos más largos.
Fig. 12. Tiempo de renderización, como se muestra en el generador de perfiles de las Herramientas para desarrolladores de React.

Cómo solucionó el problema el equipo de Fotocasa

Quita los reprocesamientos innecesarios

Los reprocesamientos ocurren cada vez que React necesita actualizar la IU con datos nuevos. Por lo general, esto proviene de una acción del usuario, una respuesta de la API o algún otro evento importante que requiere una actualización de la interfaz de usuario. Dado que cada nuevo renderizado ejecuta JavaScript, demasiados renderizados a la vez, especialmente en un árbol de componentes grande, pueden bloquear el subproceso principal y causar problemas de rendimiento.

Existen dos tipos de nuevo procesamiento:

  • Renderizaciones necesarias: Cuando un componente realmente necesita actualizarse porque posee o usa datos nuevos.
  • Renderizaciones innecesarias: Cuando un componente se actualiza sin ningún cambio significativo, a menudo debido a una administración de estado ineficiente o un manejo inadecuado de las propiedades.

Por lo general, algunos reprocesamientos innecesarios no son un gran problema, ya que React es lo suficientemente rápido como para que los usuarios no lo noten. Sin embargo, si ocurren con demasiada frecuencia o en un árbol de componentes pesado, pueden perjudicar la experiencia del usuario y afectar negativamente el INP de la página.

Este fue el caso del equipo de Fotocasa. Se dieron cuenta de que el sitio web tenía muchos nuevo renderizados innecesarios. Esto ocurrió en dos situaciones principales:

  • Durante la carga de la página: Aumentar la cantidad de tareas largas en el subproceso principal y retrasar la primera interacción, lo que afectó negativamente el INP de la página
  • Durante las interacciones del usuario: Se aumentó el tiempo de procesamiento de la mayoría de las interacciones, lo que también perjudicó el INP.

Se optimizaron muchos reprocesamientos innecesarios en el sitio web de Fotocasa. Una de las optimizaciones más importantes se realizó en la página de búsqueda. Se realizaron tres renderizaciones innecesarias durante la carga de la página. Una vez que se quitaron, se observaron los siguientes resultados:

  • Menos tareas largas (consulta la siguiente imagen)
  • Menor tiempo de bloqueo total (compara las figuras 14 y 15)
Dos instantáneas del subproceso principal de las Herramientas para desarrolladores de Chrome. La instantánea superior muestra más tareas largas antes de las optimizaciones, mientras que la instantánea inferior muestra menos tareas largas después de quitar las nuevas renderizaciones innecesarias.
Fig. 13. Instantánea del subproceso principal con y sin nuevo procesamiento innecesario.
Un informe de rendimiento para dispositivos móviles de Lighthouse que muestra un tiempo de bloqueo total de 1,080 ms, lo que indica problemas de rendimiento causados por renderizaciones innecesarias.
Fig. 14. El informe de rendimiento para dispositivos móviles de Lighthouse que muestra renderizaciones innecesarias.
Un informe de rendimiento para dispositivos móviles de Lighthouse que muestra un tiempo de bloqueo total significativamente reducido después de quitar las renderizaciones innecesarias.
Fig 15. El informe de rendimiento para dispositivos móviles de Lighthouse sin volver a renderizar innecesariamente.

Colocación de estado

La colocación incorrecta del estado de React puede ralentizar una aplicación y hacer que la IU no responda. Cuando cambia el estado de un componente, sus componentes secundarios se vuelven a renderizar de forma predeterminada, a menos que se use una solución de escape (por ejemplo, memo).

Como se explicó en la sección anterior, las nuevas renderizaciones no son inherentemente malas, pero volver a renderizar toda la página debido a una actualización de estado específica puede generar interacciones más lentas, ya que las actualizaciones del DOM se producen después de la renderización.

Por ejemplo, en la página de búsqueda, hay un diálogo que muestra todos los filtros cuando se hace clic en un botón.

La barra de filtros en la página de búsqueda de Fotocasa, que muestra un botón para abrir un diálogo con todos los filtros.
Fig. 16. Barra de filtros de Fotocasa.

En este caso, el estado que controla el estado abierto del diálogo se colocó en la página de búsqueda. Cuando cambiaba este estado, se volvía a renderizar toda la página, lo que provocaba un INP deficiente, en particular en dispositivos más lentos, como se observó cuando se usó la limitación de CPU en Herramientas para desarrolladores:

Limitación de la CPU INP
Demora de 4 veces 440 milisegundos (debe mejorar)
Demora de 6 veces 832 milisegundos (deficiente)

Cambiar el estado lo más cerca posible del componente que activa el cambio resuelve este problema. En este caso en particular, el estado se podría colocar en el componente de botón de los filtros, de modo que, cuando cambie el estado, solo se vuelva a renderizar el botón.

Limitación de la CPU INP
Demora de 4 veces 64 milisegundos (bueno)
Demora de 6 veces 232 milisegundos (debe mejorar)

Quita los estados innecesarios

Los estados no deben contener información redundante o duplicada. Si lo hacen, se podrían generar renderizaciones innecesarias y causar problemas.

Por ejemplo, en la barra de filtros de Fotocasa, hay texto que representa la cantidad de filtros aplicados para una búsqueda determinada:

La barra de filtros de Fotocasa muestra un botón etiquetado como "Filtros" con un número que indica la cantidad de filtros aplicados.
Fig. 17. Botón y contador de filtros de Fotocasa.

La cantidad de filtros aplicados se calcula a partir del estado de la aplicación. Sin embargo, esto no solo provocó una nueva renderización innecesaria de todo el componente, sino que, en ciertos casos, también generó un cambio de diseño, ya que este componente se renderiza del lado del servidor:

const [filtersCount, setFiltersCount] = useState(DEFAULT_COUNTER)

useEffect(() => {
  const counter = filters
    ? Object.keys(filters)
        ?.reduce(reducerCounter, [])
        ?.filter((param) => searchParams?.[param]).length
    : DEFAULT_COUNTER

  setFiltersCount(counter)
}, [searchParams]);

Para resolver este problema, el valor se derivó del objeto de filtros usando una variable en lugar de usar el estado:

const counter = filters
    ? Object.keys(filters)
        ?.reduce(reducerCounter, [])
        ?.filter((param) => searchParams?.[param]).length
    : DEFAULT_COUNTER;

Cómo reducir la cantidad de renderizaciones costosas

Cuando se produce una interacción en una aplicación de React, normalmente se activa un cambio de estado. Como se explicó anteriormente, cuando cambia el estado de un componente, se vuelve a renderizar junto con todos sus elementos secundarios.

Si una de estas funciones de renderización de componentes es lenta, afectará negativamente el INP de la página, ya que probablemente se generará una tarea larga y el DOM tardará más en actualizarse.

El equipo de Fotocasa intentó minimizar los cálculos que consumen mucho tiempo dentro de la función de renderización de los componentes tanto como fue posible. Las herramientas para desarrolladores de Chrome y las herramientas para desarrolladores de React fueron muy útiles para detectar operaciones de renderización lentas.

Retrasar la ejecución del código

Además de optimizar la función de renderización de los componentes, se optimizaron otras funciones para minimizar las tareas largas lo más posible. Sin embargo, algunas tareas no se pudieron optimizar porque dependían de código de terceros.

Un ejemplo fueron los análisis. En este caso, se decidió retrasar la ejecución del código de Analytics y priorizar las actualizaciones del DOM cuando se producían interacciones del usuario. Para lograrlo, el equipo de Fotocasa usó una biblioteca llamada idlefy, que también garantizó que el código de Analytics se siguiera ejecutando incluso si el navegador se cerraba inmediatamente después.

Cultura de rendimiento

El trabajo de rendimiento no es un esfuerzo único, sino algo que se debe tener en cuenta con cada función que se lanza a producción. Todos los miembros del equipo deben estar alineados, de lo contrario, las regresiones en las Métricas web esenciales son casi inevitables.

Para mantenerse al tanto de esto, el equipo de Fotocasa compartió activamente conocimientos dentro del equipo y estableció un marco de trabajo claro para identificar los problemas de rendimiento en función de los datos de RUM de Datadog de Fotocasa, incluido cómo reproducirlos. Se configuraron alertas para las Métricas web esenciales, en especial el INP, en el sistema de RUM para notificar al equipo de Fotocasa directamente en Slack. Este enfoque mantuvo el rendimiento como una prioridad y ayudó a detectar problemas antes de que se convirtieran en regresiones.

Resultados

Para mejorar el INP en Fotocasa, se requirió una combinación de optimizaciones técnicas y cambios culturales. Al eliminar las renderizaciones innecesarias, optimizar la ubicación del estado, reducir las renderizaciones costosas y aplazar el código no crítico, el equipo de Fotocasa logró que todas las páginas para computadoras de escritorio pasaran de "Necesita mejorar" a "Buena", y mejoró significativamente las páginas para dispositivos móviles, ya que actualizó casi todas las páginas "Deficiente" y "Necesita mejorar" a "Buena".

Google Search Console muestra las Core Web Vitals de Fotocasa para computadoras después de las mejoras en el INP.
Fig. 18. Google Search Console muestra las Core Web Vitals de Fotocasa para computadoras después de las mejoras en el INP.

Estos cambios mejoraron la experiencia del usuario general de Fotocasa y, junto con otras iniciativas, generaron un aumento del 27% en los anuncios de clientes potenciales por teléfono y contacto, lo que fortaleció directamente las métricas clave de la empresa.

La supervisión en tiempo real con Datadog permitió al equipo de Fotocasa validar las mejoras del INP, detectar anomalías rápidamente y evitar regresiones. Además de estos logros, Fotocasa también logró incorporar el rendimiento web en su cultura de desarrollo, lo que garantiza que el INP y las Métricas web esenciales sigan siendo una prioridad en cada lanzamiento.