Core Web Vitals 改善のお話
はじめに
こんにちは。MAMADAYS Web 担当の櫻井です。 以前のエブリーエンジニアブログにて Google の Core Web Vitals (以降 CWV) についてご紹介しました。今回は CWV のパフォーマンス改善について、MAMADAYS の Web チームが実際に行ったこと、またその結果についてをご紹介したいと思います。
ゴールとしては CWV の3指標 FID, LCP, CLS を合格基準にすることと、ベンチマークしているサイトよりも優れた数値に改善する*こととしました。
*Google の公式 FAQ によると、CWV が検索ランキングシグナルとして使われるケースは"tie-breaker"の役割が強いようで、ひとまずは競合の中で上位に入り込むことがページパフォーマンスの恩恵を受ける第一歩となります。 - What is the page experience update and how important is it compared to other ranking signals?
まずは計測してみる
パフォーマンス改善においては何よりもまず現状を計測してみることに始まります。今回はひとまず Page Speed Insights(以降 PSI)でサイトの状態を確認してみました。
MAMADAYS のとある記事ページを測定した結果、2021/01 時点では以下のようになりました。
なお、結果の見方としては一番上の数字がこの時点で測定した Lab データから算出されるスコアです。直下の「フィールド データ」は現実のユーザの体験をビッグデータとして Google が蓄積したものを反映した数値です。そのため、上のスコアと下のフィールドデータには必ずしも連動しているわけではありません。
CWV は FID, LCP が Good 圏内で、CLS が Bad 圏内。そしてスコアは 17pt。これはベンチマークしているサイトのページと比較してもワースト1位を競う非常に悪いスコアでした。
また Web パフォーマンス改善にあたって、FID, LCP, CLS の各数値については改善の結果をリアルタイムで把握したいため、PSI で表示されるフィールドデータではなくラボデータを取得・蓄積すると良いでしょう。前回の記事で紹介したように MAMADAYS ではラボデータを BigQuery に蓄積し metabase でモニタリングするようにしています。ただし、CLS に関しては正しく値を取得できなかったため、特定の記事の Lab データを毎日取得するスクリプトを作成し、モニタリングを行いました。(API は PSI API を使用)
弱点を特定する
CWV の値をある程度把握できたところで、次にどこの改善に着手すべきかを特定します。
MAMADAYS では CWV 合格へ向けて CLS の改善はもちろん、スコアを底上げするために LCP の改善も目指しました。FID はこの時点で最も合格閾値を超過している(100ms)ため、注力しないことを決めました。
具体的な改善アクションを決める際には PSI や Lighthouse が非常に役に立ちます。これらは当該サイトの何がパフォーマンス的に悪いかを親切に文章で教えてくれる機能を有しています。 PSI の結果の画面をスクロールしてみるといくつかの項目で指摘されていました。
Remove unused JavaScript
使用されていない無駄な JavaScript が読み込まれているようです。tree-shaking を適切に行い、デッドコードの除去をする必要があります。また、そもそも使われていない余分なコードをリファクタして削除するなどの整理をすると良さそうです。なお、今回はここの改善は行っていないため説明は割愛しますが、多くの場合ここを改善すれば大きく LCP が下がることが期待できます。
Defer offscreen images
画像の遅延読み込みがされていないようです。ファーストビューに表示されない画像の遅延読み込みをする必要があります。特に
sp_footer_banner@3x.png
,babyfood_merit_banner@3x.png
はファイルサイズが大きく、かつフッター部分に表示される画像なので必ず遅延読み込みをした方が良い画像です。Remove unused CSS
使用されていない無駄な CSS が読み込まれているようです。 特に
viceo-react.css
は使用率が 0%で、かなり無駄なロードになってしまっているようです。Eliminate render-blocking resources
初回レンダリングを遅くする読み込み方法のリソースがあるようです。MAMADAYS では CSS の読み込みが阻害要因となっており、読み込みタイミングの見直しが必要そうです。
Properly size images
画像のサイズが最適でないようです。ここでも一番上の画像については 93%も太っているようなので、適切にサイズを制限する必要がありそうです。
このように PSI で検査するだけで多くの改善ポイントがあることが把握できました。ただし PSI や Lighthouse ではフロントエンドの改善項目しか検査できません。例えば LCP についてはサーバーサイドやインフラの構成を見直すことでも十分に改善できることを念頭においた方がよいでしょう。
LCP の改善
LCP の改善では大きく改善が進んだポイントが3つありました。
無駄なリソースの読み込みを除去
1つ目は2月頭の -2000ms ほどの改善です。
「Remove unused CSS
」と「Eliminate render-blocking resources
」について対応しました。上記の指摘では、カルーセルを実装する slick
や、動画プレイヤーのvideo-react
が挙げられています。
Chrome Developer Tool の Coverage 機能で確認すると確かに無駄な CSS であることがわかります。
MAMADAYS では CSS を Next.js の CSS Modules で読み込みをしているため、これらの読み込み箇所を _app.js
から実際に必要なコンポーネントに移動しました。これにより不要なCSSの読み込みが除去されたことがわかります。
http2 への切り替え
2つ目は3月頭の -2200ms ほどの改善です。
これは Web 内で使われる画像の配信元 CDN のプロトコルを http/1.1 から http/2 へ切り替えたことによるものです。この切り替え設定自体は2月頭に行っていたものですが、このタイミングで PSI がリクエストを http/2 で行うように変更されたため、数値に大きく改善が現れました。
ref: March 3, 2021 | PageSpeed Insights uses http/2 to make network requests
before
after
画像を適切なサイズで配信
3つ目は3月末の -1800ms ほどの改善です。
PSI での指摘項目にあった「Properly size images
」に対応した結果でした。MAMADAYS では画像を CloudFront で配信しており、同時に Lambda Edge にてリサイズを行なっています。取得する画像の URL クエリパラメータに?w=400
などサイズを指定することでリサイズできるようにしているため、これを使ってサイズの最適化を行いました。
以下はコードの抜粋ですが、source
のmedia attribute
で sp/pc 時の画像サイズを適切に切り分けました。Retina 対応のために 2x
時の指定もsrcset attribute
で行うと良いでしょう。
また、リサイズと同時に画像タイプも WebP に変換することでよりサイズの軽量化を行なっています。
const spSize = [imgSize.sp, imgSize.sp * 2]; const pcSize = [imgSize.pc, imgSize.pc * 2]; <source type='image/webp' media='(max-width: 767px)' srcSet={`${src}?w=${spSize[0]}&fm=webp, ${src}?w=${spSize[1]}&fm=webp 2x`} /> <source type='image/webp' media='(min-width: 768px)' srcSet={`${src}?w=${pcSize[0]}&fm=webp, ${src}?w=${pcSize[1]}&fm=webp 2x`} /> <source type='image/webp' srcSet={`${src}?w=${pcSize[0]}&fm=webp, ${src}?w=${pcSize[1]}&fm=webp 2x`} /> <img src={`${src}?w=${pcSize[0]}&fm=jpg`} alt={alt} loading={loading} {...(hasSize ? { height, width } : null)} className={classnames(css.image, className)} />
改善したものの数値に影響がなかったもの
PSI の指摘項目のうち、数値に影響があまり現れないものもあります。
例えば「Defer offscreen images
」は 確かに対応した方が良いものですが多くの場合、遅延読み込みするべき画像はファーストビュー外の画像になるため、LCP の対象になるものが少ないです。そのため効果があまり現れなかったのでしょう。この辺りは改善コストを省みて実施するかを判断するのがよいでしょう。
巨人の肩に乗る(大切)
MAMADAYS Web は React 製で、フレームワークに Next.js を使用しています。Next.js はパフォーマンス観点の積極的な改善を行っており、v10.1 ではバンドルサイズが 58%も縮小されたことで純粋にロードするファイルサイズが小さくなり、LCP の向上につながります。このようにコミッティーの勢いがあり積極的に改善が行われているフレームワーク・ライブラリを選定することもパフォーマンス改善において重要になるでしょう。
Announcing Next.js 10.1:
— Vercel (@vercel) March 29, 2021
• 3x Faster Refresh (200ms faster per save)
• 58% Smaller Install (54% fewer deps)
• Webpack 5 as opt-in flag
• Apple Silicon (M1) Support
• Next.js Commerce @Shopify Integration
• More <Image> layout and loader optionshttps://t.co/swmB7h2sOg
CLS の改善
CLS の改善では主に画像の領域確保と広告の領域確保を行いました。
3月末の時点で画像のサイズ最適化と同時に width と height を指定して領域の確保を行いました。これにより 20%ほどの改善ができました。
その後に数値が大きく上ぶれてしまっているのですが、これは新機能として CLS と相性の悪い機能を実装したことによるものです。これについてはその後改善を行ったり、CLS の算出アルゴリズムが変わったことで元の水準まで戻していますが、新機能を実装する際には Web パフォーマンスの観点からも慎重に検討を行いたいところです。
CLS の算出アルゴリズムが変わったことで CLS が向上
2021/06 に Lighthouse8 がリリースされました。これを機に CLS の算出アルゴリズムが変更になりました。元々は CLS はページ滞在中全てのレイアウトシフトを累計したものになっていましたが、変更後は 5 秒間の内に発生したレイアウトシフト群の合計の中で最も値の大きいもの、というようになりました。これにより多くのサイトで CLS が改善し、MAMADAYS もその恩恵を受けることができました。詳細については以下をご参照ください。
https://web.dev/cls/#what-is-cls
スコアロジックにも変更あり
また Lighthouse8 ではスコアロジックが変わりました。各指標のスコアに反映される重み付けが変更になったのですが、以下のようになりました。 特に CLS が3倍になっているため、従前よりもレイアウトシフトを起こさない実装を心がける必要があります。
指標 | 従前 → 変更後 |
---|---|
First Contentful Paint | 15% → 10% |
Speed Index | 15% → 10% |
Largest Contentful Paint | 25% → 25% |
Time to Interactive | 15% → 10% |
Total Blocking Time | 25% → 30% |
Cumulative Layout Shift | 5% → 15% |
https://web.dev/performance-scoring/
改善の結果
この時点での PSI を測定してみると以下のようになりました。 フィールドデータは遅れて徐々に反映されるため、変化がないように見え少々分かりにくいですが、特に LCP の改善が効いたことで 20pt ほどスコアが向上しました。
これによってベンチマークしているサイトの中でもランキング上位を推移するようになりました。
今回はランキング上位に入ることはできましたが、CWV の合格基準に達することはかないませんでした。合格基準を満たせるように、MAMADAYSでは今後も改善を重ねていきます。
まとめ
今回はほとんどがフロントエンドにフォーカスした改善でしたが、より改善を進めるためにはサーバーサイドアプリケーションの改善やキャッシュの改善を行う必要があります。MAMADAYS では今後も継続的によりよい UX を提供するためパフォーマンスの改善を続けていきます。よい UX を作ることやパフォーマンスの改善に興味がある方・造詣が深い方はぜひ RECRUIT | every, Inc. までご連絡ください。