第30回 タグページをカード表示に変更し関連記事を追加する―検索・並び替えと3件の自動表示
タグ一覧を人気タグとカード型の一覧へ変更し、タグ検索と並び替えを追加。記事末尾には既存Frontmatterから最大3件の関連記事を自動表示し、既存のタグURLやnoindex、連載導線を残したまま動作を確認した記録です。

第29回では、長い記事の見出しへ直接移動できるアンカーとURLコピーを追加した。記事の中を移動する導線は増えたが、記事を探す側を見ると、タグ一覧はまだ文字リンク中心の表示だった。また、記事を最後まで読んだ後に同じ分類の記事へ移る一覧もなかった。
今回はこの2点を同じ改修で変更した。/tags/には人気タグ、カード表示、検索、並び替えを追加し、通常の記事ページには既存の分類情報から関連記事を自動表示する。
タグ機能そのものを作り直す作業ではない。第10回で追加したカテゴリ・連載・タグの導線、第13回の個別タグページnoindex, follow、第16回のタグマスタ・alias・正規化、第19回の件数順表示は残す。
- 第10回 Astroブログにカテゴリ・連載・タグの導線を追加する―Frontmatterから記事一覧を自動生成
- 第13回 ゆまラボのタグページとフッターを見直す―個別タグをnoindexにして固定ページへの導線を追加
- 第19回 タグ一覧を件数順に変更―上位50件表示、/tags/のnoindex、連載番号の表示修正
修正前のタグ一覧#
修正前の/tags/では、タグ名と記事件数が横方向へ並んでいた。表示時点では60タグあり、一覧の下に「すべて表示(60タグ)」の導線がある。

タグから個別ページへ移動できる一方、一覧には検索と並び替えがない。件数の多いタグも、それ以外も同じ見え方。
今回は参考にしたレイアウトをそのままコピーせず、ゆまラボで使っている白背景、青系の線、角丸カードに合わせる。タグ名、記事件数、URLも固定値ではなく既存データから取得する。
個別タグページは現在の構造を残す#
/tags/と/tags/<tag>/は別のページとして扱う。
修正前のAstroタグページでは、見出し、説明、記事件数、そのタグが付いた記事一覧が表示されていた。確認時点では41件の記事がある。

個別タグページには第13回でnoindex, followを設定済みなので、この指定は維持する。今回の主な変更対象は/tags/の一覧UIであり、個別ページのURL、tag slug、alias、正規化、記事一覧レイアウトは変更しない。
記事末尾には関連記事の一覧がなかった#
もう1つの対象は通常の記事ページ。
修正前は、本文末尾の「参考」が終わると、そのまま既存の末尾領域へ続いていた。本文中には必要な記事への手動リンクを置いているが、記事の分類から自動で候補を出す一覧はなかった。

関連記事は専用Frontmatterを増やさず、すでに各記事が持つcategory、subcategory、tagsから候補を選ぶ。表示件数は最大3件。候補が1件なら1件、2件なら2件だけ表示し、条件を広げて無関係な記事を埋める処理は追加しない。
既存のタグ処理を使ってカード表示へ変更#
Codexには最初に、/tags/と個別タグページの生成元、タグ件数の集計、canonical tag、alias、正規化、URL生成、個別タグページのnoindex, followを確認させた。
変更したファイルは次の6件。
src/components/TaxonomyBrowse.astro
src/pages/tags/index.astro
src/utils/posts.ts
src/pages/blog/[...slug].astro
src/layouts/ArticleLayout.astro
scripts/verify.mjs
新しいパッケージは追加していない。package.json、lockfile、Pagefind設定も変更していない。
タグ一覧の上部には「人気のタグ」を追加した。記事件数の多い順に上位7件を算出し、その下へ「すべてのタグ」を表示する。

確認画面の人気タグは、#Astro 42件、#Web制作 25件、#サイト運用 23件、#UI 12件、#Cloudflare Workers 10件、#Webデザイン 8件、#コーディング 8件の7件。
固定配列へこの7件を書いたのではなく、記事数から上位を選んでいる。「すべてのタグ」側は110件と表示され、初期画面では50件を表示する。各カードにはタグ名と記事件数を出す。
canonical tag、alias、正規化、既存URLはそのまま利用する。
タグ名検索と並び替えを追加#
「すべてのタグ」には検索欄と並び替えも追加した。
検索対象はタグ名。サイト全体のPagefind検索とは分け、タグ一覧の中だけを絞り込む。
並び替えは「記事数の多い順」と「タグ名順」の2種類。初期値は記事数の多い順にした。
動作確認では検索欄へaiを入力し、並び順を「タグ名順」へ変更した。

この状態では8件に絞られ、#AI、#AIエージェント、#aiクローラー、#ai画像生成、#email routing、#email sending、#OpenAI、#生成aiが表示された。
Pagefindの設定やサイト内検索全体には変更を入れていない。
関連記事を既存Frontmatterから選ぶ#
関連記事の候補判定はsrc/utils/posts.ts側へ追加し、記事ページを生成するsrc/pages/blog/[...slug].astroからArticleLayout.astroへ渡す構成にした。
候補は次の順で比較する。
1. 同じcategoryかつ同じsubcategory
2. 同じcategory
3. 共通するtagsの数
4. 条件が同じ場合は既存の記事順
現在表示している記事自身と同一URLの記事は除外する。draftや非公開など、既存の記事一覧で除外している記事がある場合は、そのルールをそのまま利用する。
関連記事専用Frontmatterは追加しない。カード表示にも新しい専用デザインを作らず、既存のArticleCardを再利用した。
この方式なら、新しい記事を追加したときも関連記事用の設定を別に書く必要がない。記事側で普段どおりcategory、subcategory、tagsを設定すれば、その値が候補判定にも使われる。heroImageがない記事についても関連記事だけ特別な画像処理を追加せず、現在の記事一覧で使っている既存の表示方法へ任せる。
候補が3件未満のときは件数を優先せず、該当した記事だけを出す。関連記事のために分類条件を緩め続ける処理を入れなかったので、「関連」という見出しの下へ分類の遠い記事が混ざる状態も避けられる。
記事末尾へ関連記事を表示#
修正後は、本文と参考リンクの後に「関連記事」が表示される。

確認画面では、「見出しアンカーは必要?」と「第24回 コードブロックにコピーボタンを追加」などが候補として表示されている。
配置は本文終了後、既存の連載導線や前後記事ナビゲーションより前。既存導線を削除して置き換えるのではなく、その前へ一覧を追加している。
生成HTMLでは関連記事は最大3件、自記事参照は0件。候補が0件なら空の「関連記事」見出しも表示しない。
個別タグページの表示を確認#
/tags/を変更した後、Astroの個別タグページも確認した。

確認時点の記事件数は42件。修正前の41件から件数は変わっているが、見出し、説明、記事一覧の構造は維持されている。
Codexの報告でも、既存のタグURL、タグ警告、RSS、sitemap、OGP、Pagefind、個別タグページの構成は変更していない。
ビルドと生成HTMLを確認#
実装後にnpm run buildを実行し、成功した。
生成ページ 211ページ
Pagefind 68ページ
内部リンク 8,052件
壊れたリンク 0件
タグカード 110件
人気タグ 7件
関連記事 最大3件
自記事参照 0件
PC向けは自動グリッドを使用し、狭い幅では検索欄と並び替えを縦方向へ配置するCSSになっている。長いタグ名もカード内で折り返す。
ただし、Codexを実行した環境には実機ブラウザがなかったため、狭幅表示はCSSと生成HTMLでの確認に留めている。スマートフォン実機まで確認したとは扱わない。
既存のverify.mjsも実行したが、今回とは別の記事codex-luna-astra-astro-comparisonでpubDate: 2026-09-09、updatedAt: 2026-09-12となっている既存の検証条件により停止した。タグ一覧と関連記事の実装で発生した停止ではないため、別件として記録に残している。
タグ一覧と関連記事の変更点#
/tags/では、記事数上位7件を「人気のタグ」として表示。タグ一覧もカード型へ変更した。さらにタグ名検索と「記事数の多い順/タグ名順」の切り替えを追加している。既存のタグマスタ、alias、正規化、URL、個別タグページのnoindex, followは維持している。
記事ページでは、既存のcategory、subcategory、tagsから関連記事を選び、最大3件を既存のArticleCardで表示するようにした。自記事と重複候補は除外し、候補不足時は存在する記事だけを表示する。
npm run buildは成功し、211ページを生成。内部リンク8,052件のうち壊れたリンクは0件。今回の作業ではcommit、push、deployは行っていない。


