Сборник лучших практик, которые, по мнению команды Chrome DevRel, являются наиболее эффективными способами повышения производительности Core Web Vitals в 2023 году.
За прошедшие годы мы в Google дали веб-разработчикам множество рекомендаций о том, как повысить производительность.
Хотя каждая из этих рекомендаций по отдельности может повысить производительность многих сайтов, полный набор рекомендаций, по общему признанию, огромен, и на самом деле ни один человек или сайт не сможет следовать им всем.
Если веб-производительность не является вашей повседневной работой, вероятно, не очевидно, какие рекомендации окажут наибольшее положительное влияние на ваш сайт. Например, вы, возможно, читали, что внедрение критического CSS может повысить производительность загрузки, а также, возможно, слышали, что важно оптимизировать изображения. Но если у вас нет времени работать над обеими вещами, как вы решите, какую из них выбрать?
В команде Chrome мы весь прошлый год пытались ответить на этот вопрос: какие наиболее важные рекомендации мы можем дать разработчикам, чтобы помочь им повысить производительность своих пользователей?
Чтобы адекватно ответить на этот вопрос, мы должны учитывать не только технические достоинства той или иной рекомендации, но также человеческие и организационные факторы, влияющие на вероятность того, что разработчики действительно смогут принять эти рекомендации. Другими словами, некоторые рекомендации могут быть очень эффективными в теории, но на самом деле очень немногие сайты имеют время или ресурсы для их реализации. Точно так же некоторые рекомендации имеют решающее значение, но большинство веб-сайтов уже следуют этим практикам.
Короче говоря, мы хотели, чтобы наш список лучших рекомендаций по веб-производительности был сосредоточен на:
- Рекомендации, которые, по нашему мнению, окажут наибольшее реальное влияние
- Рекомендации, актуальные и применимые к большинству сайтов.
- Рекомендации, которые реалистично реализовать для большинства разработчиков.
За последний год мы потратили много времени на проверку полного набора рекомендаций по производительности, которые мы даем, и оценку каждого из них (как качественно, так и количественно) по трем вышеуказанным критериям.
В этом посте изложены наши основные рекомендации по повышению производительности по каждому из показателей Core Web Vitals . Если вы новичок в веб-производительности или пытаетесь решить, что принесет вам наибольшую отдачу от затраченных средств, мы считаем, что эти рекомендации — лучшее место для начала.
Самая большая содержательная краска (LCP)
Наш первый набор рекомендаций касается наибольшего отрисовки содержимого (LCP) , который является мерой производительности нагрузки. Из трех основных показателей Web Vitals LCP является тем, с которым сталкивается наибольшее количество сайтов: только около половины всех сайтов в сети сегодня соответствуют рекомендуемому порогу , поэтому давайте начнем с него.
Убедитесь, что ресурс LCP доступен для обнаружения из источника HTML.
Согласно веб-альманаху HTTP Archive за 2022 год , 72% мобильных страниц имеют изображение в качестве элемента LCP, а это означает, что большинству сайтов для оптимизации своего LCP необходимо обеспечить быструю загрузку этих изображений.
Для многих разработчиков может быть неочевидно, что время, необходимое для загрузки изображения, — это лишь одна часть проблемы. Еще одна важная часть — это время до начала загрузки изображения, и данные HTTP-архива показывают, что на самом деле именно здесь многие сайты сбиваются с толку.
Фактически, из страниц, где элементом LCP было изображение, 39% этих изображений имели исходные URL-адреса, которые невозможно было обнаружить из источника HTML-документа. Другими словами, эти URL-адреса не были найдены в стандартных атрибутах HTML (таких как <img src="...">
или <link rel="preload" href="...">
), что позволило бы браузеру быстро найдите их и сразу же начните загружать.
Если странице нужно дождаться полной загрузки, анализа и обработки файлов CSS или JavaScript, прежде чем изображение сможет начать загрузку, возможно, уже слишком поздно.
Как правило, если ваш элемент LCP является изображением, URL-адрес изображения всегда должен быть доступен из источника HTML. Вот несколько советов, которые помогут сделать это возможным:
Загрузите изображение, используя элемент
<img>
с атрибутомsrc
илиsrcset
. Не используйте нестандартные атрибуты, такие какdata-src
, для рендеринга которых требуется JavaScript, поскольку это всегда будет медленнее. 9% страниц скрывают свое изображение LCP заdata-src
.Отдавайте предпочтение рендерингу на стороне сервера (SSR), а не рендерингу на стороне клиента (CSR), поскольку SSR подразумевает, что полная разметка страницы (включая изображение) присутствует в исходном HTML-коде. Решения CSR требуют запуска JavaScript, прежде чем изображение будет обнаружено.
Если на ваше изображение требуется ссылка из внешнего файла CSS или JS, вы все равно можете включить его в исходный код HTML с помощью тега
<link rel="preload">
. Обратите внимание, что изображения, на которые ссылаются встроенные стили, не обнаруживаются сканером предварительной загрузки браузера, поэтому, даже если они находятся в исходном коде HTML, их обнаружение все равно может быть заблокировано при загрузке других ресурсов, поэтому в таких случаях может помочь предварительная загрузка.
Чтобы помочь вам понять, есть ли проблемы с обнаружением вашего образа LCP, Lighthouse выпустит новый аудит в версии 10.0 (ожидается в январе 2023 г.).
Обеспечение возможности обнаружения ресурса LCP из источника HTML может привести к измеримым улучшениям, а также открывает дополнительные возможности для определения приоритета ресурса, что является нашей следующей рекомендацией.
Убедитесь, что ресурсу LCP присвоен приоритет.
Обеспечение того, чтобы ресурс LCP можно было обнаружить из источника HTML, является важным первым шагом в обеспечении того, чтобы ресурс LCP мог начать загрузку раньше, но еще одним важным шагом является обеспечение того, чтобы загрузка этого ресурса имела приоритет и не попадала в очередь позади группы. других, менее важных ресурсов.
Например, даже если ваше изображение LCP присутствует в исходном HTML с использованием стандартного тега <img>
, если ваша страница включает дюжину тегов <script>
в <head>
вашего документа перед этим тегом <img>
, это может быть за некоторое время до того, как ваш ресурс изображения начнет загружаться.
Самый простой способ решить эту проблему — дать браузеру подсказку о том, какие ресурсы имеют наивысший приоритет, установив новый атрибут fetchpriority="high"
в теге <img>
или <link>
, который загружает ваше изображение LCP. Это указывает браузеру загрузить его раньше, а не ждать завершения этих сценариев.
По данным Web Almanac, только 0,03% подходящих страниц используют преимущества этого нового API, а это означает, что у большинства сайтов в Интернете есть много возможностей улучшить LCP с минимальными усилиями. Хотя атрибут fetchpriority
в настоящее время поддерживается только в браузерах на базе Chromium, этот API представляет собой прогрессивное усовершенствование, которое другие браузеры просто игнорируют, поэтому мы настоятельно рекомендуем разработчикам использовать его сейчас.
Для браузеров, отличных от Chromium, единственный способ обеспечить приоритет ресурса LCP над другими ресурсами — это указать на него ссылку ранее в документе. Снова используя пример сайта с множеством тегов <script>
в <head>
документа, если вы хотите, чтобы ваш ресурс LCP имел приоритет перед этими ресурсами скрипта, вы можете добавить <link rel="preload">
перед любым из этих сценариев, или вы можете переместить эти сценарии ниже <img>
позже в <body>
. Хотя это работает, это менее эргономично, чем использование fetchpriority
, поэтому мы надеемся, что другие браузеры вскоре добавят поддержку.
Еще одним важным аспектом определения приоритета ресурса LCP является гарантия того, что вы не сделаете ничего, что приведет к потере его приоритета , например, добавление атрибута loading="lazy"
. Сегодня 10% страниц фактически устанавливают loading="lazy"
в своем изображении LCP. Остерегайтесь решений по оптимизации изображений, которые без разбора применяют ленивую загрузку ко всем изображениям. Если они предоставляют способ переопределить такое поведение, обязательно используйте его для образа LCP. Если вы не уверены, какое изображение будет LCP, попробуйте использовать эвристику, чтобы выбрать подходящего кандидата.
Отсрочка некритических ресурсов — это еще один способ эффективно повысить относительный приоритет ресурса LCP. Например, сценарии, которые не поддерживают пользовательский интерфейс (например, сценарии аналитики или социальные виджеты), можно безопасно отложить до тех пор, пока не произойдет событие load
, что гарантирует, что они не будут конкурировать с другими критически важными ресурсами (такими как ресурс LCP) за сеть. пропускная способность.
Подводя итог, вам следует следовать этим рекомендациям, чтобы гарантировать раннюю загрузку ресурса LCP и высокий приоритет:
- Добавьте
fetchpriority="high"
в тег<img>
вашего образа LCP. Если ресурс LCP загружается через тег<link rel="preload">
, не бойтесь, потому что вы также можете установить для негоfetchpriority="high"
! - Никогда не устанавливайте
loading="lazy"
в теге<img>
вашего образа LCP. Это приведет к потере приоритета вашего изображения и задержке его загрузки. - По возможности отложите некритические ресурсы. Либо переместив их в конец документа, используя встроенную отложенную загрузку изображений или iframe , либо загрузив их асинхронно с помощью JavaScript.
Используйте CDN для оптимизации TTFB документов и ресурсов.
Предыдущие две рекомендации были направлены на то, чтобы ваш ресурс LCP был обнаружен на ранней стадии и ему был присвоен приоритет, чтобы он мог начать загрузку сразу. Последней частью этой головоломки является обеспечение максимально быстрого получения ответа на первоначальный документ.
Браузер не может начать загрузку каких-либо подресурсов, пока не получит первый байт исходного ответа HTML-документа, и чем раньше это произойдет, тем скорее начнет происходить и все остальное.
Это время известно как время до первого байта (TTFB) , и лучший способ уменьшить TTFB — это:
- Предоставляйте свой контент как можно географически ближе к вашим пользователям.
- Кэшируйте этот контент, чтобы недавно запрошенный контент можно было быстро обработать снова.
Лучший способ сделать обе эти вещи — использовать CDN . CDN распределяют ваши ресурсы на пограничные серверы, которые разбросаны по всему миру, тем самым ограничивая расстояние, которое эти ресурсы должны пройти по сети до ваших пользователей. CDN также обычно имеют детальные элементы управления кэшированием, которые можно настроить и оптимизировать в соответствии с потребностями вашего сайта.
Многие разработчики знакомы с использованием CDN для размещения статических ресурсов, но CDN также могут обслуживать и кэшировать HTML-документы, даже те, которые генерируются динамически.
По данным Web Almanac, только 29% запросов HTML-документов были обработаны через CDN, а это означает, что у сайтов есть значительная возможность претендовать на дополнительную экономию.
Вот несколько советов по настройке CDN:
- Рассмотрите возможность увеличения продолжительности кэширования контента (например, действительно ли важно, чтобы контент всегда был свежим? Или он может устареть на несколько минут?).
- Подумайте, возможно, даже о кэшировании контента на неопределенный срок, а затем очистке кеша, если/когда вы сделаете обновление.
- Узнайте, можете ли вы переместить динамическую логику, работающую в данный момент на исходном сервере, на периферию (функция большинства современных CDN).
В общем, каждый раз, когда вы можете обслуживать контент непосредственно с периферии (избегая поездки на исходный сервер), это выигрывает в производительности. И даже в тех случаях, когда вам все же приходится возвращаться к исходному серверу, CDN обычно оптимизированы для того, чтобы делать это гораздо быстрее, так что в любом случае это победа.
Совокупное изменение макета (CLS)
Следующий набор рекомендаций касается накопительного смещения макета (CLS) , который является мерой визуальной стабильности на веб-страницах. Хотя CLS значительно улучшился в Интернете с 2020 года, около четверти веб-сайтов по-прежнему не соответствуют рекомендуемому порогу , поэтому для многих сайтов остается большая возможность улучшить свой пользовательский опыт.
Установите явные размеры для любого контента, загружаемого со страницы.
Сдвиги макета обычно происходят, когда существующий контент перемещается после завершения загрузки другого контента. Поэтому основной способ смягчить это — заранее зарезервировать необходимое пространство.
Самый простой способ исправить сдвиги макета, вызванные изображениями неразмерного размера, — это явно установить атрибуты width
и height
(или эквивалентные свойства CSS). Однако, по данным HTTP Archive, на 72% страниц имеется хотя бы одно изображение неразмерного размера. Без явного размера браузеры изначально устанавливают высоту по умолчанию 0px
и могут вызвать заметный сдвиг макета, когда изображение наконец загрузится и будут обнаружены размеры. Это представляет собой огромную возможность для коллективной сети, и эта возможность требует гораздо меньше усилий, чем некоторые другие рекомендации, предложенные в этой статье.
Также важно помнить, что изображения — не единственные элементы CLS. Сдвиги макета могут быть вызваны другим контентом, который обычно загружается после первоначального отображения страницы, включая стороннюю рекламу или встроенные видео. Свойство aspect-ratio
может помочь в борьбе с этим. Это относительно новая функция CSS, которая позволяет разработчикам явно указывать соотношение сторон изображений, а также элементов, не являющихся изображениями. Это позволит вам установить динамическую width
(например, на основе размера экрана) и заставить браузер автоматически рассчитывать соответствующую высоту, почти так же, как это происходит для изображений с размерами.
Иногда невозможно узнать точный размер динамического контента, поскольку он по своей природе динамичен. Однако даже если вы не знаете точный размер, вы все равно можете предпринять шаги, чтобы уменьшить серьезность изменений макета. Установка разумной min-height
почти всегда лучше, чем разрешение браузеру использовать высоту по умолчанию 0px
для пустого элемента. Использование min-height
также обычно является простым решением, поскольку оно по-прежнему позволяет контейнеру при необходимости вырасти до конечной высоты содержимого — оно только что уменьшило этот объем роста с полного размера до, как мы надеемся, более приемлемого уровня.
Убедитесь, что страницы имеют право на bfcache
Браузеры используют механизм навигации, называемый кэшем «назад/вперед» — или сокращенно bfcache — для мгновенной загрузки страницы из более ранней или более поздней версии истории браузера непосредственно из снимка памяти.
Bfcache обеспечивает значительную оптимизацию производительности на уровне браузера и полностью устраняет сдвиги макета во время загрузки страницы, где для многих сайтов происходит большая часть CLS. Внедрение bfcache привело к самому большому улучшению CLS , которое мы наблюдали в 2022 году.
Несмотря на это, значительное количество веб-сайтов не имеют права на использование bfcache и поэтому упускают этот бесплатный выигрыш в веб-производительности для значительного количества переходов. Если ваша страница не загружает конфиденциальную информацию, которую вы не хотите восстанавливать из памяти, вам необходимо убедиться, что ваши страницы соответствуют критериям.
Владельцы сайтов должны проверить, подходят ли их страницы для использования bfcache, и устранить причины, по которым это невозможно. В Chrome уже есть тестер bfcache в DevTools , и в этом году мы планируем улучшить этот инструментарий, добавив новый аудит Lighthouse, выполняющий аналогичный тест , и API для измерения этого в полевых условиях .
Несмотря на то, что мы включили bfcache в раздел CLS, поскольку на данный момент мы видим там самые большие успехи, bfcache, как правило, также улучшает и другие основные веб-показатели. Это один из многих способов мгновенной навигации, позволяющих значительно улучшить навигацию по страницам.
Избегайте анимаций/переходов, в которых используются свойства CSS, определяющие макет.
Другой распространенный источник изменений макета — анимация элементов. Например, баннеры файлов cookie или другие баннеры уведомлений, которые выдвигаются сверху или снизу, часто способствуют CLS. Это особенно проблематично, когда эти баннеры оттесняют другой контент, но даже если это не так, их анимация все равно может повлиять на CLS.
Хотя данные HTTP-архива не могут окончательно связать анимацию со сдвигами макета, данные показывают, что страницы, которые анимируют любое свойство CSS, которое может повлиять на макет, на 15% менее вероятно будут иметь «хороший» CLS, чем страницы в целом. Некоторые свойства связаны с худшим CLS, чем другие. Например, страницы, которые анимируют ширину margin
или border
, имеют «плохой» CLS почти в два раза чаще, чем страницы в целом оцениваются как плохие.
Возможно, это неудивительно, потому что каждый раз, когда вы перемещаете или анимируете какое-либо свойство CSS, вызывающее макет, это приводит к сдвигам макета , и если эти сдвиги макета не происходят в пределах 500 миллисекунд после взаимодействия с пользователем, они повлияют на CLS.
Что может удивить некоторых разработчиков, так это то, что это справедливо даже в тех случаях, когда элемент вынесен за пределы обычного потока документов. Например, абсолютно позиционированные элементы, которые анимируют top
left
будут вызывать сдвиги макета, даже если они не перемещают другой контент. Однако если вместо анимации top
или left
вы анимируете transform:translateX()
или transform:translateY()
, это не заставит браузер обновлять макет страницы и, следовательно, не приведет к каким-либо изменениям макета.
Предпочтение анимации свойств CSS, которые можно обновлять в потоке компоновщика браузера, уже давно является лучшим методом повышения производительности, поскольку при этом вся работа переносится на графический процессор, а не на основной поток. Помимо того, что это общая рекомендация по повышению производительности, это также может помочь улучшить CLS.
Как правило, никогда не анимируйте и не перемещайте никакие свойства CSS, требующие от браузера обновления макета страницы, если только вы не делаете это в ответ на касание пользователя или нажатие клавиши (но не hover
). И всякий раз, когда это возможно, отдавайте предпочтение переходам и анимации, используя свойство transform
CSS.
Аудит Lighthouse «Избегайте некомпозитной анимации» предупредит, когда страница анимирует потенциально медленные свойства CSS.
Первая входная задержка (FID)
Наш последний набор рекомендаций касается задержки первого ввода (FID) , которая является мерой реакции страницы на взаимодействие с пользователем. Хотя большинство сайтов в Интернете в настоящее время имеют очень хорошие показатели по FID, в прошлом мы документировали недостатки показателя FID и считаем, что у сайтов еще есть много возможностей улучшить свою общую реакцию на взаимодействие с пользователем.
Наша новая метрика «Взаимодействие с следующей отрисовкой» (INP) является возможным преемником FID, и все приведенные ниже рекомендации одинаково хорошо применимы как к FID, так и к INP. Учитывая, что сайты работают хуже с INP, чем с FID, особенно на мобильных устройствах, мы рекомендуем разработчикам серьезно рассмотреть эти рекомендации по отзывчивости, несмотря на «хороший» FID.
Избегайте или разбивайте длинные задачи
Задачи — это любая часть дискретной работы, которую выполняет браузер. Задачи включают рендеринг, компоновку, анализ, а также компиляцию и выполнение сценариев. Когда задачи становятся длинными — то есть 50 миллисекунд или дольше — они блокируют возможность основного потока быстро реагировать на вводимые пользователем данные.
Согласно Веб-альманаху, существует множество свидетельств того, что разработчики могли бы делать больше, чтобы избежать или разбить длинные задачи. Хотя разбиение длинных задач может оказаться не таким простым, как другие рекомендации в этой статье, оно требует меньше усилий, чем другие методы, не предложенные в этой статье.
Хотя вы всегда должны стремиться выполнять как можно меньше работы в JavaScript, вы можете немного помочь основному потоку , разбивая длинные задачи на более мелкие . Этого можно добиться, часто передавая основной поток , чтобы обновления рендеринга и другие взаимодействия с пользователем могли происходить быстрее.
Другой вариант — рассмотреть возможность использования таких API, как isInputPending
и Scheduler API . isInputPending
— это функция, которая возвращает логическое значение, указывающее, ожидает ли пользовательский ввод. Если он возвращает true
, вы можете передать основной поток, чтобы он мог обработать ожидающий ввод пользователя.
API планировщика — это более продвинутый подход, который позволяет планировать работу на основе системы приоритетов, учитывающей, является ли выполняемая работа видимой для пользователя или фоновой.
Разбивая длинные задачи, вы даете браузеру больше возможностей для выполнения важной, видимой для пользователя работы, такой как взаимодействие и любые связанные с этим обновления рендеринга.
Избегайте ненужного JavaScript
В этом нет никаких сомнений: веб-сайты используют больше JavaScript, чем когда-либо прежде , и эта тенденция, похоже, не изменится в ближайшее время. Когда вы отправляете слишком много JavaScript, вы создаете среду, в которой задачи конкурируют за внимание основного потока. Это определенно может повлиять на скорость реагирования вашего сайта, особенно в решающий период запуска.
Однако это не неразрешимая проблема. У вас есть несколько вариантов:
- Используйте инструмент покрытия в Chrome DevTools, чтобы найти неиспользуемый код в ресурсах вашего веб-сайта. Уменьшив размер ресурсов, необходимых во время запуска, вы можете гарантировать, что ваш веб-сайт будет тратить меньше времени на анализ и компиляцию кода, что приведет к более плавному первоначальному взаимодействию с пользователем.
- Иногда неиспользуемый код, который вы найдете с помощью инструмента покрытия, помечается как «неиспользуемый», поскольку он не выполнялся во время запуска, но все еще необходим для некоторых функций в будущем. Это код, который вы можете переместить в отдельный пакет посредством разделения кода .
- Если вы используете диспетчер тегов, обязательно периодически проверяйте свои теги, чтобы убедиться, что они оптимизированы или даже используются ли они еще. Старые теги с неиспользуемым кодом можно удалить, чтобы сделать JavaScript вашего менеджера тегов меньше и эффективнее.
Избегайте больших обновлений рендеринга
JavaScript — не единственное, что может повлиять на отзывчивость вашего сайта. Рендеринг сам по себе может быть дорогостоящей работой, и когда происходят большие обновления рендеринга, они могут помешать вашему веб-сайту реагировать на вводимые пользователем данные.
Оптимизация работы по рендерингу — непростой процесс, и он часто зависит от того, чего вы пытаетесь достичь. Тем не менее, есть некоторые вещи, которые вы можете сделать, чтобы обновления рендеринга были разумными и не разрастались на длинные задачи:
- Избегайте использования
requestAnimationFrame()
для выполнения какой-либо невизуальной работы. ВызовыrequestAnimationFrame()
обрабатываются на этапе рендеринга цикла событий, и если на этом этапе выполняется слишком много работы, обновления рендеринга могут быть отложены. Очень важно, чтобы любая работа, которую вы выполняете с помощьюrequestAnimationFrame()
была зарезервирована исключительно для задач, связанных с отрисовкой обновлений. - Сохраняйте размер DOM небольшим . Размер DOM и интенсивность работы по верстке коррелируют. Когда средству визуализации необходимо обновить макет для очень большого DOM, работа, необходимая для перерасчета его макета, может значительно увеличиться.
- Используйте сдерживание CSS . Включение CSS зависит от свойства CSS
contain
, которое дает браузеру инструкции о том, как выполнять работу с макетом для контейнера, для которого установлено свойствоcontain
, включая даже изоляцию области макета и рендеринг в определенном корне в DOM. Это не всегда простой процесс, но, изолируя области, содержащие сложные макеты, вы можете избежать ненужной работы по макетированию и рендерингу.
Заключение
Улучшение производительности страниц может показаться сложной задачей, особенно если учесть, что в Интернете можно принять во внимание множество рекомендаций. Однако, сосредоточив внимание на этих рекомендациях, вы сможете подойти к проблеме целенаправленно и целеустремленно и, надеюсь, продвинуть иглу в основных веб-жизненных показателях вашего веб-сайта.
Хотя перечисленные здесь рекомендации ни в коем случае не являются исчерпывающими, мы полагаем (основываясь на тщательном анализе состояния Интернета), что эти рекомендации являются наиболее эффективными способами, с помощью которых сайты могут улучшить свои основные веб-показатели в 2023 году.
Если вы хотите выйти за рамки перечисленных здесь рекомендаций, ознакомьтесь с этими руководствами по оптимизации для получения дополнительной информации:
Наступающий новый год и более быстрый Интернет для всех! Пусть ваши сайты будут быстрыми для ваших пользователей во всех наиболее важных аспектах.
Фото Девина Эйвери