kaji.blog

このサイトについてのサムネイル2026/09/14

##このサイトについて

このサイトについて

はじめまして。このサイトの最初の投稿です。

記念すべき1本目なので、このポートフォリオサイトがどういう仕組みで動いているのか、そしてなぜこの構成にしたのかを紹介します。

GitHubを丸ごとCMSにする

このサイトの一番の特徴は、管理画面を持たないことです。

記事も制作物も、すべてこのportfolioリポジトリのGitHub Issuesとして書いています。今読んでいるこの投稿も、実体は1つのIssueです。

  • Issueのタイトル → 記事タイトル
  • Issue本文 → Markdown本文
  • ラベル → カテゴリ(type:)・タグ(tag:)・公開状態(status:)
  • 作成日時・更新日時 → 投稿日・更新日

さらに、本文の先頭にHTMLコメントを1つ埋め込んで、descriptionやサムネイル画像などMarkdownで表現しづらいメタ情報もそこに含めています。ビルド時にこのコメントだけ抜き出してパースし、本文からは取り除いてから表示する、という形です。

普段からコードを書く延長で、Issueを立てるだけで記事が書ける。ブラウザでもGitHub CLIでもスマホアプリでも投稿できる。専用の管理画面を作らなくていい。この身軽さがやりたかったことです。

ビルドとデプロイの流れ

裏側の仕組みはシンプルです。

GitHub Issues

GitHub Actions

GitHub GraphQL API取得

Astro Build

GitHub Pages

Issueが作成・編集されたり、ラベルが変わったりすると、GitHub Actionsが起動します。GraphQL経由で公開状態のIssueをすべて取得し、Astroで静的サイトとしてビルドして、GitHub Pagesに自動デプロイする、という流れです。

ラベルにはstatus:draft / status:published / status:archivedのような公開状態を持たせていて、status:publishedが付いたタイミングで初めてサイトに反映されます。逆に外せば、サイトから消えます。

Issueの取得からAstroのページに載るまでの間には、もう少し細かい工程があります。

  1. status:ラベルが変化した時点で、まずzodスキーマによるバリデーションが走ります。ステータスやタイプのラベルが重複していないか、必須のメタ情報が揃っているかをCI上でチェックし、問題があればstatus:draftに戻してデプロイを止めます
  2. バリデーションを通過したら、AstroののカスタムローダーとしてIssue一覧を取得し、記事データに変換します
  3. 本文中の画像はGitHubの添付リンクのままだと消える可能性があるため、ビルド時にダウンロードしてpublic配下に保存し直しています。使われなくなった画像はcleanAssetsスクリプトで定期的に掃除しています

かなり地味な工程の積み重ねですが、これのおかげで「ラベルを貼るだけで安全に公開できる」という体験が成り立っています。

使っている技術

  • Astro — 静的サイトジェネレーター。表示速度を重視
  • TypeScript
  • Vanilla CSS — フレームワークに頼らず素のCSSで組んでいます
  • GitHub Actions / GitHub Pages — ビルドと公開
  • GitHub GraphQL API — Issueの取得

サーバーもデータベースも持たない、完全に静的なサイトです。

これから

コア機能の実装は完了したので、Beta版リリースへ向けサイトのデザインを主に整えていきます。また、タグの検索や表示の機能を追加しサイトを完成させ、継続的な記事執筆や制作物の更新を行っていきます。。