Core Web Vitalsとは——Googleの品質指標
Googleは2021年からCore Web Vitalsをランキング要因に採用しています。これはユーザー体験を定量化した3つの指標です。
| 指標 | 意味 | 良い値 |
|---|---|---|
| LCP(Largest Contentful Paint) | 最大コンテンツの表示時間 | 2.5秒以内 |
| FID/INP(Interaction to Next Paint) | 入力応答性 | 200ms以内 |
| CLS(Cumulative Layout Shift) | レイアウトシフト量 | 0.1以下 |
計測ツール
# Chrome DevTools
# → Lighthouseタブ → 「Generate report」
# PageSpeed Insights(オンライン)
# https://pagespeed.web.dev/
# Web Vitals Chrome拡張機能
# リアルユーザー計測に近いデータが確認できる
LCP(最大コンテンツの表示)を改善する
LCPはヒーロー画像や大見出しなど、ビューポート内の最大要素が表示されるまでの時間です。
画像の最適化
<!-- NG:大きな画像をそのまま使う -->
<img src="hero.jpg" alt="ヒーロー画像">
<!-- OK:最適化された画像 -->
<picture>
<source type="image/webp"
srcset="hero-400.webp 400w, hero-800.webp 800w, hero-1200.webp 1200w"
sizes="(max-width: 768px) 100vw, 1200px">
<img src="hero-800.jpg"
alt="ヒーロー画像"
width="1200"
height="600"
loading="eager"
fetchpriority="high">
</picture>
preloadでLCPを先読みする
<head>
<!-- LCP要素の画像を先読み -->
<link rel="preload"
as="image"
href="hero-800.webp"
imagesrcset="hero-400.webp 400w, hero-800.webp 800w"
imagesizes="(max-width: 768px) 100vw, 800px">
</head>
CLS(レイアウトシフト)を防ぐ
画像や広告が読み込まれた際に他の要素が動いてしまう現象がCLSです。
<!-- NG:画像にサイズを指定しない -->
<img src="product.jpg" alt="商品">
<!-- OK:width・heightでアスペクト比を確保 -->
<img src="product.jpg" alt="商品" width="600" height="400">
<!-- Tailwindでアスペクト比を固定 -->
<div class="aspect-[4/3] bg-gray-100 overflow-hidden">
<img src="product.jpg" class="w-full h-full object-cover" alt="商品" loading="lazy">
</div>
/* フォントのCLSを防ぐ:font-displayを指定 */
@font-face {
font-family: 'Noto Sans JP';
font-display: swap; /* 代替フォントで表示して、読み込み後に切り替え */
src: url('/fonts/noto-sans-jp.woff2') format('woff2');
}
JavaScriptの最適化
重いJavaScriptはメインスレッドをブロックしてINP(入力応答性)を悪化させます。
<!-- NG:パース完了を待ってから実行 -->
<script src="app.js"></script>
<!-- OK:非同期ダウンロード・DOM構築後に実行 -->
<script src="app.js" defer></script>
<!-- 独立したスクリプトは async -->
<script src="analytics.js" async></script>
// NG:重い処理をメインスレッドで実行
function heavyComputation() {
// 100万件ループなど
}
heavyComputation(); // UIがフリーズ
// OK:Web Workerで別スレッドに移す
const worker = new Worker('/workers/heavy.js');
worker.postMessage({ data: largeData });
worker.onmessage = (e) => {
console.log('処理結果:', e.data);
};
CSSの最適化
<!-- NG:巨大なCSSを1ファイルにまとめる -->
<link rel="stylesheet" href="all.css">
<!-- OK:クリティカルCSSをインライン化 -->
<style>
/* above-the-fold のスタイルだけをインライン化 */
body { margin: 0; background: #faf9f7; }
.hero { min-height: 80vh; ... }
</style>
<!-- 残りのCSSは非同期で読み込む -->
<link rel="preload" href="app.css" as="style" onload="this.onload=null;this.rel='stylesheet'">
LaravelでのVite最適化
// vite.config.js
import { defineConfig } from 'vite';
import laravel from 'laravel-vite-plugin';
export default defineConfig({
plugins: [
laravel({
input: ['resources/css/app.css', 'resources/js/app.js'],
refresh: true,
}),
],
build: {
rollupOptions: {
output: {
// チャンク分割でページごとに必要なJSだけ読み込む
manualChunks: {
'vendor': ['axios'],
'alpine': ['alpinejs'],
},
},
},
},
});
サーバー側の最適化
// Laravelでのレスポンス圧縮
// .htaccessまたはNginx設定
// Gzip / Brotli圧縮を有効化
// HTTPキャッシュヘッダー
return response($html)
->header('Cache-Control', 'public, max-age=3600')
->header('ETag', md5($html));
// 静的アセットの長期キャッシュ(Viteのコンテンツハッシュ)
// app.abc1234.js → max-age=31536000
まとめ
Core Web Vitalsの改善は画像最適化・CLS防止・JavaScriptの非同期化の3本柱で対応できます。弊社ではWebサイト制作時にPageSpeed Insights 90点以上を目標に最適化を実施しています。
Webサイトの表示速度改善・SEO対策についてはお気軽にご相談ください。