AstroのContent Collectionsでfrontmatterを型チェックする設定

AstroでMarkdown記事を増やすなら、frontmatterの型を先に決めておくと楽です。

title の書き忘れや pubDate の型違いは、記事数が増えるほど見落としやすくなります。Content Collectionsのschemaを使うと、このあたりをコード側でチェックできます。

公式ドキュメントでは、Content Collectionsのschema定義が案内されています。

https://docs.astro.build/en/guides/content-collections/#defining-the-collection-schema

content.config.ts

import { defineCollection } from 'astro:content';
import { glob } from 'astro/loaders';
import { z } from 'astro/zod';

const posts = defineCollection({
  loader: glob({ pattern: '**/*.md', base: './src/content/posts' }),
  schema: z.object({
    title: z.string(),
    description: z.string().optional(),
    pubDate: z.coerce.date(),
    draft: z.boolean().default(false),
    tags: z.array(z.string()).default([]),
  }),
});

export const collections = { posts };

この設定で、Markdown記事のfrontmatterを型として扱えます。

Markdown側

---
title: "記事タイトル"
description: "記事の説明文"
pubDate: 2026-06-28
draft: false
tags: ["Astro", "Markdown"]
---

pubDatez.coerce.date() にしておくと、文字列からDateへ変換できます。

draftを持たせる

draft は最初から入れておくと便利です。

draft: z.boolean().default(false)

記事一覧や詳細ページで、draft を除外できます。

const posts = await getCollection('posts', ({ data }) => !data.draft);

getCollection() の使い方は公式リファレンスにあります。

https://docs.astro.build/en/reference/modules/astro-content/#getcollection

まとめ

AstroでMarkdown記事を管理するなら、Content Collectionsのschemaを先に決めます。

  • title は必須
  • description はSEOや一覧で使う
  • pubDatez.coerce.date()
  • draft は公開制御に使う
  • tags はタグページや関連記事に使う

frontmatterのルールを曖昧にしないだけで、記事追加のミスを減らせます。

関連記事

参考