Hugo

Cloudflare Web Analytics の LCP がひどかったので Google Fonts をやめた

TL;DR — 日本語 Google Fonts(M PLUS Rounded 1c)は初回訪問者の LCP を大幅に悪化させる。システムフォントに切り替えれば外部フォントリクエストがゼロになる。

このブログの Cloudflare Web Analytics を眺めていたら、LCP(Largest Contentful Paint)の評価がなかなかひどいことになっていた。

Cloudflare Web Analytics の Core Web Vitals。LCP が Good 0%、Needs Improvement 50%、Poor 50%

体感では全然遅くないんだけどなぁ、と思いつつ、Claude さんに原因を調べてもらった。

結論:Google Fonts

Claude さん、さすがに早い。表題の通りの結論でした。

どうやら、デザインで使っていた、M+PLUS+Rounded+1c という日本語の丸ゴシックフォントが犯人。

グリフ数が数万文字規模になるので、ファイルサイズが英字フォントとは桁違いに重いとのこと。

詳しく説明してもらいました。

Hugo の設定を見たら、こういう記述があった。

googleFontsLink = "https://fonts.googleapis.com/css2?family=M+PLUS+Rounded+1c:wght@300;400;700&family=JetBrains+Mono:wght@400;500&display=swap"

しかも外部 CDN(fonts.googleapis.com)へのリクエストが発生するので:

  1. DNS 解決
  2. TCP 接続
  3. TLS ハンドシェイク
  4. フォント CSS の取得
  5. 実際のフォントファイルの取得

という連鎖が初回訪問のクリティカルパスに入ってくる。LCP がテキスト要素(見出し)だったとすれば、フォントが読み込まれるまでレンダリングがブロックされる。

体感と計測がズレる理由

キャッシュだよ、キャッシュ。

Claude さんに言われて気づいたわ。

自分のブラウザに既にあるんだもん、そりゃ速いはずだよ。

Cloudflare Web Analytics は実際の訪問者のブラウザで計測した RUM(Real User Monitoring)データを集めている。

訪問者のほとんどは初回訪問でキャッシュなし。

Lighthouse スコア 64 の正体を調べたら、シミュレーションだった話

TL;DR — Lighthouse のスコアは「低速 4G シミュレーション」値なので実測とは乖離する。実測(WebPageTest)で 713ms なら対応不要と判断できる。アクセシビリティのコントラスト問題は修正済み。

Chrome の Lighthouse でこのブログのパフォーマンスを測ったら 64/100 という微妙なスコアが出た。
「さすがにまずいかな」と思って調査してみたら、想定外の結論にたどり着いたのでメモ。

状況

Lighthouse の JSON レポートを取得して Claude Code に分析させた。

スコアはこんな感じ:

カテゴリスコア
Performance64
Accessibility94
Best Practices100
SEO100

Performance と Accessibility に問題あり。

Accessibility の問題: コントラスト比

こっちはシンプルだった。

シンタックスハイライトの CSS(monokai テーマ)で、JSON のキー名や XML タグに使われるピンク赤(#f92672)が、背景色(#272822)に対してコントラスト比 3.92:1 しかなかった。WCAG AA 基準は 4.5:1 以上なので落第。

Lighthouse のレポートで指摘されていた要素:

selector: code.language-json > span.line > span.cl > span.nt
explanation: contrast ratio of 3.92 (foreground: #f92672, background: #272822)

該当するトークンを全部拾うと .nt(NameTag)、.kn(KeywordNamespace)、.o(Operator)、.ow(OperatorWord)、.gd(GenericDeleted)の 5 種類。