【早見表】Next.js fetchのcacheオプションのまとめ
Next.jsでは、fetch() における キャッシュの設定 がアプリの性能と動作に大きく影響します。特にApp Routerでの開発時は、デフォルトの動作を正しく理解しておくことで、不要なAPIリクエストや表示のラグを防げます。
fetchのキャッシュ戦略 早見表
cache オプション | 説明 | 使うべきケース |
|---|---|---|
force-cache | 常にキャッシュを使う(デフォルト) | 静的データを取得する時 |
no-store | キャッシュせず、常にネットワークアクセス | 毎回最新のデータが必要な時 |
reload | ブラウザのキャッシュを使わず、サーバー再取得 | 手動で明示的に使う特殊ケース |
default | fetch実行元の環境に依存(Serverならforce-cache) | App Routerでは明示したほうが安全 |
only-if-cached | キャッシュにある場合のみ使用。失敗することもある | 実験用途に近い |
App Routerでの挙動とデフォルトの落とし穴
Next.js 13以降のApp Routerでは、fetch()は基本的にビルド時の静的キャッシュ(Static Generation)を使います。これは以下のようなコードでも同様です:
ts// app/page.tsx
export default async function Page() {
const res = await fetch('https://example.com/api/data');
const data = await res.json();
return <pre>{JSON.stringify(data)}</pre>;
}
上記コードは、デフォルトで force-cache が適用され、example.com のデータは ビルド時に1回だけ取得され、以後キャッシュされます。
具体例①:常に最新のデータが必要なケース
tsexport default async function Dashboard() {
const res = await fetch('https://api.example.com/stats', {
cache: 'no-store'
});
const stats = await res.json();
return <div>{stats.visitorCount}</div>;
}
- リアルタイムなアクセス数などを表示したい場合に適しています。
- キャッシュを使わないため、リクエストは常にAPIへ直接飛びます。
- ISR(Incremental Static Regeneration)ではなく、SSR的な動作になります。
具体例②:静的なブログ記事の取得
tsexport default async function BlogList() {
const res = await fetch('https://cms.example.com/posts', {
next: { revalidate: 3600 } // 1時間ごとに再取得
});
const posts = await res.json();
return <ul>{posts.map(p => <li key={p.id}>{p.title}</li>)}</ul>;
}
revalidateにより、ISRが有効化され、キャッシュとリアルタイム取得の良いとこ取りができます。- 再生成のタイミングを指定可能。
cache: 'force-cache'相当だが、再取得タイミングを設定できるのが利点。
cacheとnextオプションの違いと併用例
| オプション | 用途 | 例 |
|---|---|---|
cache | fetchのキャッシュ挙動 | cache: 'no-store' |
next.revalidate | ISRの再取得間隔 | next: { revalidate: 10 } |
ts// ISRで動的なリビルドが必要なとき
await fetch('https://api.example.com/articles', {
next: { revalidate: 60 }
});
よくある落とし穴
no-storeを使わないと、再デプロイしない限りデータが更新されないことがある- App Routerでは**
getServerSidePropsは使えない**ので、fetch時の設定がSSR/SSGを分ける鍵になる cache: 'no-store'を連発すると、API呼び出しが多くなり、パフォーマンスに悪影響を与える可能性がある
まとめ:キャッシュ戦略選びの指針
| ケース | 推奨設定 |
|---|---|
| 毎回最新の情報が必要 | cache: 'no-store' |
| 頻繁に変わらないが定期的に更新される | next: { revalidate: 秒数 } |
| 完全に静的(例:マークダウン記事) | デフォルト(force-cache) |
Next.jsのfetchは非常に柔軟で、キャッシュ戦略を適切に使い分けることでパフォーマンスと鮮度のバランスが取れるよう設計されています。
用途に応じた最適な設定を行うことで、UXとSEOの両立も実現できます。
articleNext.js の キャッシュ無効化設計:タグ・パス・スケジュールの 3 軸でコントロール
articleNext.js Metadata API 逆引き:`robots`/`alternates`/`openGraph`/`twitter` の記入例
articleNext.js を Bun で動かす開発環境:起動速度・互換性・落とし穴
articleNext.js Edge Runtime vs Node Runtime:TTFB・コールドスタート・コストを実測検証
articleNext.js の Route Handlers で multipart/form-data が受け取れない問題の切り分け術
articleNext.js Server Components 時代のデータ取得戦略:fetch キャッシュと再検証の新常識
articleCursor エディタ:キャッシュクリアで動作改善!Windows/Mac での手順とマウスカーソルの直し方
articlePinia ストアスキーマの変更管理:バージョン付与・マイグレーション・互換ポリシー
articleshadcn/ui コンポーネント置換マップ:用途別に最短でたどり着く選定表
articleOllama のコスト最適化:モデルサイズ・VRAM 使用量・バッチ化の実践
articleRemix Loader/Action チートシート:Request/Response API 逆引き大全
articleObsidian タスク運用の最適解:Tasks + Periodic Notes で計画と実行を接続
blogiPhone 17シリーズの発表!全モデルiPhone 16から進化したポイントを見やすく整理
blogGoogleストアから訂正案内!Pixel 10ポイント有効期限「1年」表示は誤りだった
blog【2025年8月】Googleストア「ストアポイント」は1年表記はミス?2年ルールとの整合性を検証
blogGoogleストアの注文キャンセルはなぜ起きる?Pixel 10購入前に知るべき注意点
blogPixcel 10シリーズの発表!全モデル Pixcel 9 から進化したポイントを見やすく整理
blogフロントエンドエンジニアの成長戦略:コーチングで最速スキルアップする方法
review今の自分に満足していますか?『持たざる者の逆襲 まだ何者でもない君へ』溝口勇児
reviewついに語られた業界の裏側!『フジテレビの正体』堀江貴文が描くテレビ局の本当の姿
review愛する勇気を持てば人生が変わる!『幸せになる勇気』岸見一郎・古賀史健のアドラー実践編で真の幸福を手に入れる
review週末を変えれば年収も変わる!『世界の一流は「休日」に何をしているのか』越川慎司の一流週末メソッド
review新しい自分に会いに行こう!『自分の変え方』村岡大樹の認知科学コーチングで人生リセット
review科学革命から AI 時代へ!『サピエンス全史 下巻』ユヴァル・ノア・ハラリが予見する人類の未来