Nuxt 2サイトをバニラHTML静的サイトに作り替えてCloudflare Pagesへ移行した
Nuxt 2で動いていた地域密着サービス業のサイトを、フレームワークなしのバニラHTML/CSS/JSに書き直した。デプロイ先もNetlifyからCloudflare Pagesに変えた。朝から手を動かし始めて、カスタムドメインのDNSレコードを切り替え終わるまでに丸一日かかった。Cloudflare Pagesのビルド設定でつまずく場面が多く、ターミナルとダッシュボードを何度も往復した。
なぜ作り替えたか
- Nuxt 2のメンテナンスが終了しており、依存パッケージの脆弱性警告が溜まっていた
- サイトの内容は固定的で、SPA/SSRの仕組みが不要だった
- フレームワークを外すことでビルド時間・デプロイサイズともに削減できる
結論として、バニラHTMLに戻す判断は正解だった。ビルドステップが消えてデプロイが数秒で終わる。
やったこと
1. Nuxt 2 → バニラHTML/CSS/JSへのリビルド
Nuxt 2のコンポーネント構造を解体して、素のHTMLファイルに再構成した。CSSはインラインではなく外部ファイルに分離し、JSは最低限のインタラクション(ハンバーガーメニュー、スムーズスクロール等)だけ残した。
2. npm → pnpm への移行
パッケージマネージャをnpmからpnpmに切り替えた。package-lock.json を削除して pnpm import は使わず、pnpm install でクリーンに pnpm-lock.yaml を生成した。
3. Netlify → Cloudflare Pages への移行
ここが一番時間を食った。Cloudflare Pagesのビルド設定で複数の問題にぶつかった。
Node.js v12 問題
Cloudflare Pagesのデフォルトビルド環境がNode.js v12だった。pnpmが動かない。ダッシュボードの環境変数で NODE_VERSION を設定して解決した。
NODE_VERSION = 20
npm ci 問題
Cloudflare Pagesのビルドコマンドがデフォルトで npm ci を実行しようとする。pnpmに切り替えたのに package-lock.json がないとエラーになる。ビルドコマンドを明示的に指定して回避した。
wrangler設定
wrangler.toml は不要だった。静的サイトの場合、Cloudflareダッシュボードからの設定だけで済む。最初にwrangler.tomlを置いてしまい、設定の競合でビルドが失敗した。削除して解決。
4. ヒーロー動画の切り出し
サイトトップに置くヒーロー動画を元素材(C0130.MP4)から切り出した。
ffmpeg -ss 00:01:25 -to 00:01:39 -i C0130.MP4 \
-vf scale=-2:720 -c:v libx264 -crf 28 -preset slow \
-an hero.mp4
- 元素材の1:25〜1:39の14秒間を抽出
- 720pにリサイズ、音声なし
- 出力サイズ: 約1.8MB
-crf 28 と -preset slow の組み合わせで、画質を保ちつつファイルサイズを抑えた。Webで使う動画は2MB以下を目安にしている。
5. カスタムドメイン設定
Netlify向けに設定していたDNSレコードをCloudflare Pages向けに書き換えた。
- Netlifyの
Aレコード(104.198.14.52等)を削除 - Cloudflare Pagesの
CNAMEレコードに変更 - DNS伝播を確認して、HTTPS接続が通ることを検証
6. Netlifyサイトの削除
DNSの切り替えが完了し、Cloudflare Pages側でサイトが正常に表示されることを確認した後、Netlifyのプロジェクトを削除した。
学んだこと
- Cloudflare Pagesのデフォルトビルド環境は古い。
NODE_VERSION環境変数の設定を真っ先にやるべき - 静的サイトにwrangler.tomlは要らない。Workersを使わない限り、ダッシュボード設定で完結する
- ffmpegの
-ssをインプットの前に置くとシーク速度が上がる。出力品質とのトレードオフで使い分ける - pnpmへ移行するとき、CIのビルドコマンドも忘れずに変える。ローカルで動いてもCI側が
npm ciを叩いてコケるパターンは定番
振り返り
フレームワークを外してバニラに戻す作業自体は1〜2時間で終わった。残りの時間はCloudflare Pagesのビルド設定との格闘に費やした。エラーメッセージを読んで、環境変数を一つ足して、ビルドを再実行する。このサイクルを5回以上繰り返した。ローカルでは一発で動くのにCIで落ちる、という状況はいつまで経っても慣れない。
ただ、移行が終わってみると、Cloudflare Pagesのデプロイ速度はNetlifyより体感で速い。GitHubにpushしてから10秒程度でデプロイが完了する。静的サイト+Cloudflare Pagesの組み合わせは、今後の小規模サイトのデフォルト構成にしてよさそうだ。