Next.jsとmicroCMSでつくる、運用しやすいニュース一覧
コーポレートサイトやサービスサイトでよく必要になる「ニュース一覧」。 更新頻度は高いのに、都度エンジニアがHTMLを編集する運用ではスピードが出ません。 そこで本記事では、Next.js App RouterとmicroCMSを組み合わせ、 入稿しやすく、表示も速く、保守もしやすいニュース一覧を実装します。
Concept
なぜニュース一覧にヘッドレスCMSを使うのか
ニュースやお知らせは、公開日、タイトル、カテゴリ、本文、外部リンク、アイキャッチなど、 構造化された情報の集合です。HTMLへ直接書き込むと、更新作業が属人化し、 表記ゆれや公開漏れが起きやすくなります。
microCMSのようなヘッドレスCMSを使うと、編集者は管理画面からニュースを入稿し、 フロントエンドはAPI経由で必要なデータだけを取得できます。 Next.js側ではページ表示、キャッシュ、ルーティング、SEOを担当するため、 「編集しやすい管理画面」と「速いWebサイト」を分離して運用できます。
入稿
担当者がmicroCMSでニュースを登録します。
取得
Next.jsがAPIから一覧データを取得します。
表示
カード型の一覧としてサイトに反映します。
Schema
microCMS側のAPI設計
まずmicroCMSに「news」というAPIを作成します。ニュース一覧では、 後から絞り込みや詳細ページへ拡張できるよう、最低限以下のフィールドを用意しておくと扱いやすくなります。
API名: news
エンドポイント: news
フィールド例:
- title: テキストフィールド
- publishedAt: 日時
- category: セレクトフィールド
- body: リッチエディタ
- excerpt: テキストエリア
- eyecatch: 画像
- slug: テキストフィールド
ポイントは、表示に必要な情報をあらかじめ分けておくことです。 一覧ページでは本文全文ではなく、title、publishedAt、category、excerptなどに絞って取得すると、 レスポンスが軽くなり、表示ロジックもシンプルになります。
Setup
Next.jsプロジェクトの準備
App Router構成のNext.jsプロジェクトに、microCMS公式SDKを追加します。 APIキーやサービスドメインは公開リポジトリへ含めず、環境変数で管理します。
npm install microcms-js-sdk
# .env.local
MICROCMS_SERVICE_DOMAIN=your-service-domain
MICROCMS_API_KEY=your-api-key
lib/microcms.ts
import { createClient } from "microcms-js-sdk";
if (!process.env.MICROCMS_SERVICE_DOMAIN) {
throw new Error("MICROCMS_SERVICE_DOMAIN is required");
}
if (!process.env.MICROCMS_API_KEY) {
throw new Error("MICROCMS_API_KEY is required");
}
export const client = createClient({
serviceDomain: process.env.MICROCMS_SERVICE_DOMAIN,
apiKey: process.env.MICROCMS_API_KEY,
});
APIクライアントを1か所にまとめておくと、一覧、詳細、カテゴリ一覧などへ拡張するときも再利用できます。 また、環境変数が未設定のままビルドされる事故を早期に検知できます。
Source
ニュース一覧を取得するコード
ニュース一覧では、取得件数、並び順、取得フィールドを明示します。 以下では公開日が新しい順に10件取得し、一覧に必要なフィールドだけを指定しています。
// lib/news.ts
import { client } from "./microcms";
export type NewsItem = {
id: string;
title: string;
publishedAt: string;
category?: string;
excerpt?: string;
slug?: string;
};
export async function getNewsList() {
return await client.getList<NewsItem>({
endpoint: "news",
queries: {
limit: 10,
orders: "-publishedAt",
fields: "id,title,publishedAt,category,excerpt,slug",
},
});
}
app/news/page.tsx
import Link from "next/link";
import { getNewsList } from "@/lib/news";
export const revalidate = 300;
function formatDate(value: string) {
return new Intl.DateTimeFormat("ja-JP", {
year: "numeric",
month: "2-digit",
day: "2-digit",
}).format(new Date(value));
}
export default async function NewsPage() {
const data = await getNewsList();
return (
<main className="newsPage">
<div className="newsHeader">
<p className="eyebrow">News</p>
<h1>お知らせ</h1>
<p>サービス、イベント、採用、メディア掲載などの最新情報をお届けします。</p>
</div>
<div className="newsList">
{data.contents.map((item) => (
<article className="newsCard" key={item.id}>
<time dateTime={item.publishedAt}>{formatDate(item.publishedAt)}</time>
{item.category && <span className="category">{item.category}</span>}
<h2>
<Link href={`/news/${item.slug ?? item.id}`}>
{item.title}
</Link>
</h2>
{item.excerpt && <p>{item.excerpt}</p>}
</article>
))}
</div>
</main>
);
}
export const revalidate = 300; は、一定間隔でページを再検証する設定です。
ニュースのように「即時性は必要だが、毎アクセスでAPIを叩くほどではない」コンテンツでは、
表示速度と更新性のバランスを取りやすくなります。
Operation
運用しやすくするための設計ポイント
1. 一覧用の抜粋フィールドを用意する
本文から自動で切り出す方法もありますが、句読点やHTMLタグの影響で意図しない表示になることがあります。 一覧用のexcerptを編集者が入力できるようにしておくと、トップページやニュース一覧で使い回しやすくなります。
2. カテゴリは自由入力より選択式にする
「イベント」「Event」「イベント情報」のような表記ゆれを防ぐため、 カテゴリはセレクトフィールドや参照フィールドで管理するのがおすすめです。 将来的にカテゴリ絞り込みを実装する場合も、データが整っているほど楽になります。
3. APIキーは読み取り専用に近い権限で扱う
フロントエンドから使うAPIキーは、必要最小限の権限にするのが基本です。 ニュース一覧の表示だけであれば、原則として取得に必要な権限だけを使います。
4. 詳細ページへの拡張を見越してslugを持たせる
一覧だけならidでも表示できますが、URLを読みやすくしたい場合はslugを用意します。
例として /news/site-renewal のようなURLにすると、
共有時にも内容が伝わりやすくなります。
Conclusion
まとめ
Next.jsとmicroCMSを組み合わせると、ニュース一覧のような更新型コンテンツを、 編集者にとって扱いやすく、開発者にとって保守しやすい形で構築できます。 App Routerでサーバー側取得を行い、必要なフィールドだけを取得し、 再検証の設定を入れることで、パフォーマンスと運用性を両立できます。
小さなニュース一覧でも、初期設計で「誰が更新するのか」「どの情報を一覧に出すのか」 「将来的に詳細ページやカテゴリ絞り込みが必要になるか」を整理しておくと、 長く使えるCMS連携になります。