ページは速く読み込まれるのに、まだ遅く感じますか?

Lighthouseのレポートはグリーンです。LCPとCLSのスコアも良好です。ページの読み込みも速いです。それなのに、実際のユーザー環境(Real World)でのスコアが低下します。その理由がわかりません。

その原因の多くはINPにあります。

INPとは「Interaction to Next Paint」の略です。2024年3月に、Core Web Vitalsの指標としてFIDに代わり採用されました。FIDは最初のクリックの遅延のみを測定していましたが、INPはユーザーがページを使用している間のすべてのインタラクションを測定し、その中で最も遅いものを報告します。

INPは読み込みの指標ではなく、応答性(レスポンス)の指標です。INPが問うのはただ一つ、「クリックやタイピングをしたとき、画面が変化するまでにどれくらいの時間がかかるか?」ということです。

Googleは以下の基準を用いています:

サイトの読み込みが1秒で完了しても、スコアが低くなることはあります。「速く読み込むこと」と「速く反応すること」は、全く別のタスクなのです。

Lighthouseはボタンをタップしてくれるわけではありません。あくまで推定値を示すだけです。そのため、ラボ環境(Lab Data)のレポートがグリーンでも、フィールド環境(Field Data)のスコアがレッドになることがあり得ます。

実数を確認するには、インタラクションが発生した瞬間に測定する必要があります。以下のコードを使用してください:

import { onINP } from 'web-vitals';
onINP(function (metric) {
  console.log('INP', metric.value, metric.entries);
});

これにより、遅いインタラクションとその原因となった要素がログに記録されます。これで、推測ではなく実際の問題に対処できるようになります。

INPの問題は、メインスレッドがビジー状態のときに発生します。JavaScriptのタスクが完了するまで、ブラウザはレスポンスを描画(paint)できません。長時間実行されるタスク(Long Task)がインタラクションをブロックしてしまうのです。

よくある原因:

長いタスクを分割することで、これを解決できます。ブラウザに「息をつく暇」を与えてあげましょう。

async function onClick() {
  doUrgentPart(); 
  await yieldToMain(); 
  doExpensivePart(); 
}

目標は、重い処理が始まる前にレスポンスを描画することです。

その他の対策:

ラボ環境のレポートがグリーンなのに、実際のスコアがレッドであるなら、LCPを眺めるのはやめましょう。インタラクションの測定に移ってください。

Source: https://dev.to/lamas51/your-page-loads-fast-but-still-feels-slow-its-inp-not-load-time-2gkn