Представьте себе сценарий, в котором вы нажимаете на элемент и ожидаете ответа, но элемент не выглядит так, как будто на него нажали, и он не отвечает, поэтому вы нажимаете снова. Однако эти два щелчка после завершения ответа приводят к отмене действия, которое вы хотели. С тобой когда-нибудь случалось? Звучит обескураживающе, не так ли?

Это тот опыт, который мы, веб-инженеры, не можем позволить себе дать пользователям. И причин, которые могут привести к этому, может быть множество. Если бы вы регулярно проверяли производительность своих приложений, вы бы сталкивались с предложениями по разделению кода вашего приложения и уменьшению отправляемого JavaScript. В этом посте мы рассмотрим причины медленного отклика приложения, способы измерения медлительности и подходы к ее улучшению.

TL;DR
Некоторые задачи при взаимодействии с пользователем могут блокироваться, мешать работе пользователя и приводить к низкому показателю INP.

Возможны следующие способы оптимизации:

  • Держите задачи небольшими и посвященными тому, что они должны делать.
  • использовать API-интерфейс планировщика Chrome для планирования задач для браузера
  • выносить важные задачи в основной поток

Давайте сначала разберемся, почему взаимодействие с пользователем может быть медленным. Когда пользователь взаимодействует с элементом в браузере, пользовательский агент воспринимает это как одну задачу и ставит ее в очередь в списке задач для браузера. Эта единственная задача может занять больше или меньше времени в зависимости от типа операции, которую необходимо выполнить. Некоторые задачи занимают больше времени, что приводит к тому, что основной поток занят их выполнением, а другие задачи тем временем блокируются.

Длинные задачи

Задача считается длинной, если она превышает 50ms для выполнения и 50ms для ответа, в основном, более чем 100ms. Ожидается, что веб-сайт, на котором нет длительных задач, будет отвечать в течение 100ms как по времени выполнения, так и по времени отклика на ввод данных пользователем, в соответствии с RAIL.

Согласно данным из веб-альманаха, интересно отметить, что средняя мобильная страница имеет тенденцию иметь 19 длинных задач.

Вот тут-то и появляется INP. INP — это метрика отклика, расшифровывается как Interaction to next paint, которая измеряет время с момента, когда пользователь взаимодействовал со страницей, до того момента, когда на странице действительно был виден следующий кадр. Хорошей мерой INP является наименьшее время между взаимодействием и обратной связью в результате этого взаимодействия.
Взаимодействие может означать такие события, как tap, click, keyUp, pointerdown и т. д.

Интересная статья здесь о том, как на самом деле измеряется INP.

.

INP рассчитывается путем отслеживания всех взаимодействий со страницей. Выбранное значение является процентилем этих взаимодействий. Затем используется формула для выбора высокого процентиля этих взаимодействий.

То, как мы помещаем жизненно важные веб-меры в корзины «Хорошо», «Требует улучшения», «Плохо», вот как выглядит «хорошо» и «плохо» для метрики INP.

Чтобы рассчитать общую скорость отклика страницы, показатель INP рассчитывается, когда пользователь уходит со страницы, и он включает в себя все взаимодействия, такие как события мыши, события клавиатуры, касание/нажатие на устройстве с сенсорным экраном.

ПИД / ИНФ?

Я помню, как анализировал свои веб-сайты и всегда был доволен хотя бы одной метрикой из трех основных веб-жизненных показателей 😀 — задержкой первого ввода. Немного поднимет мое эго, что я точно делаю что-то хорошее. Но если мы посмотрим на картину в целом, то заметим, что большинство веб-сайтов имеют хорошее значение FID, даже если скорость отклика не так велика.
И чтобы решить эту проблему, был введен INP с улучшенным подходом к измерению. . INP измеряет не только первое взаимодействие, но и все взаимодействия на странице, в отличие от FID. Кроме того, как следует из названия, INP измеряет время до следующей отрисовки, в отличие от FID, который измеряет время только до тех пор, пока не произойдет обработка.

Если мы посмотрим на показатели INP на мобильных устройствах, 55% веб-сайтов имеют хороший показатель INP, а 36% нуждаются в улучшении. Однако, в случае FID, 92% веб-сайтов имеют «хороший» FID. Таким образом, более высокая скорость отклика с помощью INP уже снизила оценку «хорошо».

Также интересно видеть, что показатель INP имеет тенденцию быть обратно пропорциональным популярности веб-сайта, согласно данным из главы «Производительность в веб-альманахе».

При лучшем подходе к измерению скорости отклика веб-сайта с помощью INP разработчикам было бы разумно начать рассматривать эту метрику как важную проверку производительности, а также с учетом того, что Google рассматривает возможность замены FID на INP в качестве одного из основных жизненно важных веб-сайтов.

При рассмотрении мобильного опыта по рейтингу сайтов 52% из 1000 лучших веб-сайтов попадают в категорию хороших с показателем FID, однако только 20% проходят с хорошим статусом с показателем INP, а это огромная разница. намекая на необходимость действительно улучшить общую ситуацию с отзывчивостью, поскольку длительные задачи являются одной из вещей, которые необходимо решить.

Могу ли я отслеживать значение INP моего веб-сайта?

Один из крутых способов отслеживать взаимодействие нашего веб-сайта с реальными данными от пользователей — использовать библиотеку web-vitals.

Библиотека предлагает метод onINP, который возвращает тип события вместе со значением INP.

Мы могли бы записать эти данные, а затем получить их через какой-либо API или поставщика аналитики, чтобы понять причины измерения INP на основе реального использования в полевых условиях.

Что-то вроде этого:

import {onINP} from 'web-vitals';
onINP(({name, value, attribution}) => {
  console.log(name)
  console.log(value)
  console.log(attribution.eventType)
});

Это дает нам меру нашего INP и помогает нам лучше понять, как мы можем улучшить эту задержку взаимодействия.

Так выглядел общий балл INP на сайтах по данным веб-альманаха.

Как найти длинную задачу в своем приложении?

К настоящему времени мы уже знаем, как работает значение INP, и следующим шагом будет профилирование нашего приложения и просмотр областей улучшения. Для этого мы идем прямо к профилировщику производительности и определяем длинные задачи (те, которые превышают порог 50ms).

Как мы видим, есть много длинных задач, приводящих к более медленному ответу пользователя на ввод, одна из которых имеет задержку 676ms.

И по мере того, как мы углубляемся, это дает нам некоторое представление об операциях, заставляющих это значение увеличиваться до 600ms здесь:

Попробуем сейчас оптимизировать одну такую ​​длинную задачу. Могут быть разные подходы к улучшению длинных задач, один из которых заключается в разбиении ваших длинных задач на более мелкие выделенные задачи.

Например, длинная задача, описанная выше, которая заняла 600ms, была задачей блокировки для обновлений, связанных с пользовательским интерфейсом, и, таким образом, привела бы к нарушению работы пользователей, поскольку они увидели бы отложенный ответ. Что, если задача по-прежнему делает именно то, что она делает, но она разбита на несколько задач с небольшими операциями, что означает:

  • Задача 1 — Только для шага querySelector
  • Задача 2 — разбор
  • Задача 3 — получить операции
  • Задача 4 — removeChild
    и так далее.

Подробнее читайте здесь 👇🏻