bizlp-gas-accounting プロジェクト向け詳細レポート


TL;DR

  • インベントリ: docs/_internal/ は番号付きサブディレクトリ+ディレクトリ単位の README.md(人間の目次)と、リポジトリ全体は mkdocs.ymldocs/SUMMARY.md を「単一の真実」として持つ二層構成が、ソロ〜2人体制では最もコストパフォーマンスが高い。CIで「nav 未登録ファイル」を mkdocs build --strict + validation.nav.omitted_files: warn で自動検出すれば、発見可能性と網羅性を同時に担保できる。
  • カバレッジギャップ: 「書いたつもりで書いてない」問題は、status: planned のスタブファイル方式(空ファイルを意図的に登録)+ ADR Accepted/コードマージ時の GitHub Actions フックで早期検出するのが現実的。週次の「棚卸し(status: planned が30日以上動かないものを警告)」を1本のスクリプトで回せば6ヶ月後も再発しない。
  • status 値域: ソロ〜小規模では planned / draft / active / deprecated / superseded の5値が最小実用解。archived は当面導入せず、deprecated + 30日ルールで運用。AGENTS.md / CLAUDE.md には「カバレッジギャップ一覧」を機械可読リンクで埋め込み、Claude Code が「未着手」を「未着手」として認識できるようにする。

Q1. ドキュメントインベントリ管理の業界パターン

1.1 インデックスファイル方式(README.md / SUMMARY.md)

GitBook 由来の慣習である SUMMARY.md(=目次ファイル)は、MkDocs 系プラグイン mkdocs-literate-nav(oprypin 作)に引き継がれ、現在は最も移植性の高い「ナビゲーション兼インベントリ」フォーマットになっている。同プラグインのドキュメントは「SUMMARY.md is the default value of nav_file. The plugin takes care to not let MkDocs complain if you don't end up using the nav document as an actual page of your doc site」と明記しており、GitHub 上で直接 Markdown として閲覧できることが利点として強調されている。

限界: 単一の SUMMARY.md だけに頼ると、ファイル数が50を超えたあたりから「手動更新の漏れ=orphan(孤児)ファイル」が急増する。実例として MkDocs issue #1755 は「someone will write new documentation but forget to include it in the nav configuration」を明確な failure mode として列挙している。

1.2 YAML frontmatter によるメタデータ管理

各ツールのデファクト frontmatter キー:

ツール状態管理キー値域
Docusaurus 3.xdraft, unlisted (boolean)true/false。unlisted: true は本番ビルドには含むが nav から隠す
Jekyllpublished (boolean)デフォルト true
Hugodraft, expiryDate, publishDatedraft は production で除外
MkDocs (Material)カスタム(プラグイン依存)プラグインで status を解釈
Obsidian慣習なし。Dataview で任意キーをクエリ可能
NotionStatus propertyTo Do / In Progress / Complete の3カテゴリ+カスタム

Docusaurus は当初 status enum(DRAFT / UNLISTED / UNPUBLISHED / PUBLISHED)を提案する Discussion #4697 があったが、結局 boolean 2つ(draft / unlisted)に収束した。これは「enum よりも boolean のほうが小規模では誤運用が少ない」という設計判断の好例。

1.3 nav 定義ファイルをインベントリとして兼用

  • MkDocs: mkdocs.ymlnav: セクション。プラグインを使えば階層を SUMMARY.md に逃がせる。
  • Docusaurus: sidebars.js / sidebars.ts。autogenerated モードでディレクトリから自動生成可。
  • GitBook: SUMMARY.md(旧版)/ 専用 CMS(新版)。
  • Hugo / Jekyll: ディレクトリ構造そのものがインベントリ(コンベンション・オーバー・コンフィギュレーション)。

「nav 定義をインベントリとして兼用する」アプローチの最大の利点は、CI で nav 未登録ファイルを --strict ビルドで失敗させられること。MkDocs 公式ドキュメントは次の設定を「Recommended settings for most sites (maximal strictness)」として例示している:

validation:
  omitted_files: warn
  absolute_links: warn
  unrecognized_links: warn
  anchors: warn

そして「The warn level is, of course, intended for use with mkdocs build --strict (where it becomes an error), which you can employ in continuous testing.」と明示している。

1.4 CI で orphan files を自動検出する実例

(a) MkDocs --strict モード — 上記 1.3 の通り、業界標準。MkDocs issue #1875 のログには INFO - The following pages exist in the docs directory, but are not included in the "nav" configuration: - index.md - management.md - tech.md のように 未登録ファイルを名指しで報告する 出力例が残っている。

(b) Lychee(lycheeverse/lychee-action) — 公式 GitHub Action が用意されており、.github/workflows/links.yml に数行で組み込める。ただしこれは「リンク切れ」検出であり、厳密な orphan ファイル検出ではない点に注意。

(c) HashiCorp terraform-provider-kubernetes — 実プロジェクトの参考実装として、.github/workflows/markdown-link-check.yamlgaurav-nelson/github-action-markdown-link-check を使った CI が公開されている。

(d) Zenzic — MkDocs / Zensical 用の docs リンター。「Nav-aware routing: with explicit nav, files present on disk but absent from nav are classified as ORPHAN_BUT_EXISTING」という明示的な orphan 検出機能を持つ。

(e) Kubernetes website — 興味深いことに、巨大 OSS でも markdown validation 専用の CI を持たないプロジェクトは多い(issue #54795 に「Currently, these issues are mostly detected during manual review」と記録あり)。**つまり「小規模だからやらない」のではなく、「やっている組織のほうが少数派」**であり、bizlp が CI を入れること自体が競争優位になる。

1.5 AI エージェント文脈での最適化事例

  • GitBook の skill.md: 2026年2月24日付の公式ブログ(Tal Gluck 著「skill.md explained: How to structure your product for AI agents」)で「A strong skill.md file reduces guesswork and improves reliability. And by grounding AI behavior in authoritative product documentation, it also helps minimize hallucinations.」と述べ、AI エージェント向けの専用ファイルを「ドキュメントサイト内に置く」運用を推奨。
  • OpenAI の AGENTS.md: agents.md 公式は「At time of writing the main OpenAI repo has 88 AGENTS.md files」と明記しており、サブディレクトリごとに AGENTS.md を置く階層型運用 がデファクト化しつつある。
  • Anthropic 公式 (How Anthropic teams use Claude Code, PDF): 「Claude Code reads their Claude.md files (documentation), identifies relevant files for specific tasks, explains data pipeline dependencies… This replaces traditional data catalogs and discoverability tools」と内部運用を公開。CLAUDE.md が「データカタログ/インベントリ的役割」を担う事例。
  • Andrej Karpathy の llm-wiki Gist: Obsidian のグラフビューで orphan を視覚的に検出し、Dataview クエリで index.md を動的生成、CLAUDE.md schema を「最重要アーティファクト」と位置づける運用例。「Obsidian's graph view makes orphan detection visual, no separate audit step needed」と述べる。

1.6 arc42 / Diátaxis とインベントリ管理の関係

  • arc42 はインベントリではなく「12の引き出し(drawers)」というコンテンツ構造のテンプレート。INNOQ の Gernot Starke は「The cabinet has a value, even if certain compartments remain empty」と述べ、空でも構造を持つことを許容している。つまり arc42 と「status: planned のスタブ運用」は哲学的に整合する。
  • Diátaxis はカテゴリ分類(Tutorial / How-to / Reference / Explanation)であり、これもインベントリではない。公式ドキュメントは「don't try to work on the big picture」「small, responsive iterations」を推奨しており、トップダウンで全カバレッジを設計するアプローチを明示的に否定している。bizlp の _internal/ 30本に Diátaxis を導入するなら、4分類ごとのサブディレクトリではなく「frontmatter diataxis: how-to|reference|... タグ」での運用が小規模向き。

Claude 固有の観点: 業界記事は arc42 と Diátaxis を「両立する」と書きがちだが、実は arc42 はソフトウェアアーキテクチャ用、Diátaxis はユーザー向け技術文書用 であり、対象読者が異なる。bizlp の場合、ADR・アーキテクチャ仕様は arc42、運用ドキュメント(_internal/)は Diátaxis という棲み分けが現実的。


Q2. カバレッジギャップ検出の手法

2.1 スタブ慣習(status: planned

メリット:

  • ファイルが存在するため、grep / find / Claude Code の検索でヒットする → 「不在」を明示的に表現できる。
  • CI で「status: planned かつ最終更新から30日以上経過」を警告できる(後述のスクリプト例)。

デメリット / failure modes:

  • 空ファイルが増えると「nav の見た目が荒れる」(Docusaurus の draft: true が production で隠される機能はここで効く)。
  • スタブを作ったまま忘れる「スタブ墓場」化。週次レビューが必須。

実例: Docusaurus は draft: true で「production build から完全に除外」、unlisted: true で「URLは生きるが sidebar から隠す」という2モードを提供。bizlp の場合、_internal/ は production deploy がないため draft ではなく status: planned メタデータでの管理が妥当。

2.2 チェックリスト方式(ADR の Consequences に列挙)

MADR 4.0 公式テンプレートは status: {proposed | rejected | accepted | deprecated | … | superseded by ADR-0123} という frontmatter を採用しており、ADR 自身に派生ドキュメント化必須事項を列挙する慣習がある。例えば「ADR-0045 で docs/_internal/ 組織化を Accepted → Consequences に『_internal/00-overview.md_internal/10-runbooks/README.md を作成する必要がある』と明記」というパターン。

Atlassian の Definition of Done 解説 は「All documentation written and updated」を DoD 条件として例示しており、コード変更とドキュメント更新を一体のチケットで管理するアプローチを推奨。

2.3 イベントトリガー方式(CI / pre-commit)

  • pre-commit フレームワーク(pre-commit.com): .pre-commit-config.yaml でフックを宣言。
  • GitHub Actions: PR ごとに paths: ['docs/**', 'mkdocs.yml'] フィルタで docs CI を回す。
  • 具体的シナリオ:
    • ADR が Accepted になったとき: PR の diff に status: accepted が含まれていたら、Consequences セクションを正規表現で抽出 → 「必要ドキュメント一覧」を Issue 化(GitHub Actions の actions/github-script)。
    • コードマージ時: src/ の変更 PR に docs/ の変更が含まれない場合、PR にラベル needs-docs を付与(Danger.js や reviewdog で実装可)。

2.4 定期棚卸し方式

  • 週次: status: planned で最終更新が30日以上前のファイルを Slack / メール通知(CI cron)。
  • 月次: 全 ADR の status を git log で再確認し、コードと矛盾するものを deprecated に降格。
  • 四半期: arc42 の各セクションが空のままになっていないか目視。

2.5 組み合わせとチームサイズ別推奨

チームサイズ推奨組み合わせ
ソロ(〜1名)スタブ + 週次棚卸し(CI cron)のみ。イベントトリガーは過剰。
2〜3名+ ADR Accepted イベントトリガー + frontmatter schema 検証
4〜5名+ コードマージ時の needs-docs ラベル運用 + 月次レビュー会
6名以上テクニカルライター専任化を検討。本レポートの推奨は適用外。

failure mode: 「ベストプラクティス」として広く言われているが小規模では裏目に出るパターン:

  • 全ファイルに last_reviewed: YYYY-MM-DD 必須化 → 機械的更新で日付だけ進めるアンチパターン化しやすい。
  • doc coverage を100%目指す → 意図的な未記録(=口頭で済む些末事項)を曖昧化する。「意図的な未記録」を表現するキー(例: status: wontdoc)を別途用意するほうが健全

Q3. frontmatter status フィールドの設計

3.1 値域の比較

パターン値域由来
ADR (Nygard)Proposed / Accepted / Deprecated / Superseded4値最小
MADR 4.0proposed / rejected / accepted / deprecated / superseded by ADR-NNNN5値
Notion (組み込み)To do / In progress / Complete + サブカテゴリ3カテゴリ
Docusaurusdraft + unlisted (boolean 2軸)2軸独立
Notion 編集ワークフロー(事例)Draft / In Review / Approved / In Progress / Shipped / Archived6値

3.2 小規模で維持可能な最小値域: 5値

bizlp 向け推奨:

status:
  - planned     # スタブ。中身がない。作る予定だけある
  - draft       # 書き始めたが未完。レビュー不要
  - active      # 現行ドキュメント。Claude Code が信頼してよい
  - deprecated  # 古い。新規参照非推奨だが履歴として残す
  - superseded  # 完全に置き換えられた。supersededBy で後継を指す

archived を別途設けるか? → 当面は不要。理由は (1) archived と deprecated の運用差は小規模では実質ゼロ、(2) Git 履歴が archive を兼ねる、(3) 値域が6に増えると「どれを使うか迷う」コストが上回る。将来 ADR が100本を超えたら導入を検討。

3.3 planned(スタブ)の運用ルール

  • 空ファイル許容: ただし # TODO: ... の1行と、frontmatter 必須項目(type, status, audience, owner, planned_for)を持つこと。
  • CI チェック:
    • ファイルサイズが200バイト未満 かつ status が planned 以外 → エラー(書き忘れ)。
    • status: planned かつ最終 git commit から30日経過 → 警告(スタブ墓場検出)。

3.4 deprecated vs archived の使い分け

INNOQ や techworld-with-milan の ADR 解説では「Once an ADR is accepted, it is immutable. If the conclusion changes, a new ADR is written that supersedes the old one and updates the old one's status field」と明記される。つまり ADR の世界では:

  • deprecated = 「もうこの決定に従うべきではないが、別の決定で明示的に置換されたわけではない」
  • superseded = 「ADR-0123 によって置き換えられた」

bizlp の運用ドキュメントでは archived「履歴目的のみ、Claude Code は読まないでよい」 という機械可読フラグとして将来導入する余地は残す。

3.5 ADR との整合性

bizlp は ADR を 45本持っているため、frontmatter は _internal/ と ADR で同じ enum を使ったほうが Claude Code への説明コストが下がる。提案:

# 共通: docs/_internal/*.md と docs/adr/*.md で同じ schema
type: adr | spec | runbook | guide | reference
status: planned | draft | active | deprecated | superseded
audience: developer | operator | future-self
owner: @username
supersededBy: ADR-0046  # status: superseded のときのみ必須

ただし ADR は append-only(INNOQ・MADR・log4brains が口を揃えて主張)なので、active という値は ADR には使わず accepted を使い分けたほうがよい。最終提案は §「本プロジェクトへの推奨」へ。


Q4. AI エージェントとドキュメントカバレッジ

4.1 「存在しないドキュメントへの参照」検出

設計パターン:

  1. AGENTS.md / CLAUDE.md に「ドキュメント目録」を埋め込む: agents.md 公式は「the closest one to the file being edited takes precedence」と述べ、サブディレクトリごとに AGENTS.md を置くことを推奨。bizlp なら docs/_internal/AGENTS.md に「ここにあるべきドキュメント一覧(status と一緒に)」を列挙。
  2. status: planned スタブを実ファイルとして置く: Claude Code がファイル検索で見つけたとき、frontmatter の status: planned を読んで「未着手」と認識できる。
  3. docs/_internal/COVERAGE_GAPS.md を専用ファイルとして維持: AGENTS.md からリンクし、「現時点で口頭でしか決まっていない/検討中で保留のもの」を一覧化。Augment Code のブログ記事「A good AGENTS.md is a model upgrade. A bad one is worse than no docs at all.」(2026年4月22日、Slava Zhenylenko 著)によれば「Warning-only documentation consistently underperformed documentation that paired prohibitions with a concrete alternative」とされており、「これは未文書化」とだけ書くのではなく「未文書化なので、ユーザーに確認すること」と次のアクションを明示するのが鍵。

4.2 status: planned を Claude Code に認識させる

CLAUDE.md に1行追加:

## Documentation status conventions
Each file under `docs/` has a `status` field in its YAML frontmatter.
- `planned`: stub file, content NOT YET written. Do not assume the file's content; ask the user.
- `draft`: partial content, may be inconsistent.
- `active`: trusted, up-to-date.
- `deprecated`: do not use for new decisions; read only for historical context.
- `superseded`: replaced. Follow `supersededBy` to the successor.

Anthropic 公式の reduce-hallucinations ガイドが「Allow Claude to say 'I don't know': Explicitly give Claude permission to admit uncertainty. This simple technique can drastically reduce false information」と述べる通り、「不在」を明示的に許容する記述を CLAUDE.md に置くことが、Claude Code が幻覚しない条件。

4.3 AGENTS.md / CLAUDE.md にカバレッジギャップ一覧を記載する運用コスト

  • コスト: ファイルは平均週1回更新 → Claude Code に「COVERAGE_GAPS.md を更新して」と指示するだけで自動化可能。手動コストはほぼゼロ。
  • リスク: CLAUDE.md / AGENTS.md は context window を食う。HumanLayer のブログは「Frontier thinking LLMs can follow ~ 150-200 instructions with reasonable consistency」と警告。ギャップ一覧は AGENTS.md に直書きせず、AGENTS.md → COVERAGE_GAPS.md → 個別ファイル のリンク階層で progressive disclosure とする。Anthropic の公式ベストプラクティス(TurboDocx blog による要約: 「Anthropic's official best practices documentation is clear: your CLAUDE.md should be concise. The recommended target is under 200 lines. Some teams go as low as 60 lines. The absolute ceiling is roughly 300 lines before Claude starts losing signal in the noise.」)に従い、200行を上限の目安とする。

4.4 Anthropic 公式の CLAUDE.md / AGENTS.md ガイドライン

  • 公式 (code.claude.com/docs/en/best-practices): 「Run /init to generate a starter CLAUDE.md file based on your current project structure, then refine over time. CLAUDE.md is a special file that Claude reads at the start of every conversation. Include Bash commands, code style, and workflow rules.」
  • 公式の落とし穴指摘: 「The over-specified CLAUDE.md: If your CLAUDE.md is too long, Claude ignores half of them because important rules get buried in noise. Fix: Ruthlessly prune.」
  • Anthropic のエンジニアリングブログ: 「The root file should be pointers and critical gotchas only; everything else drifts into noise.」
  • 公式 reduce-hallucinations: 「External knowledge restriction: Explicitly instruct Claude to only use information from provided documents and not its general knowledge.」

なお、Anthropic は AGENTS.md フォーマットそのものは公式採用していないが、Claude Code は AGENTS.md も読むコミュニティ慣習があり、共存可能。

4.5 リポジトリ内ドキュメント参照を最適化する prompting パターン

  • 「Read CLAUDE.md, then read docs/_internal/AGENTS.md, then proceed」: 階層的読み込みを明示。
  • 「Before assuming any architectural fact, check docs/adr/. If not found, say 'no ADR exists' and ask」: 不在の明示を強制。
  • エンファシス・マーカー: Anthropic 公式は「marking a rule as IMPORTANT increases the probability that Claude treats it as a priority constraint」と確認。bizlp の CLAUDE.md には **IMPORTANT**: If a doc has status: planned, treat its content as nonexistent. のように1〜2箇所だけ強調を使う。

Q5. 推奨アーキテクチャの提案(bizlp-gas-accounting 特化)

5.1 全体構成

bizlp-gas-accounting/
├── CLAUDE.md                          # 200行以内、規約とポインタのみ
├── AGENTS.md                          # CLAUDE.md と同等(symlink でも可)
├── docs/
│   ├── README.md                      # 人間向けエントリポイント
│   ├── SUMMARY.md                     # 全ドキュメント目次(CIで自動生成可)
│   ├── COVERAGE_GAPS.md               # 未文書化事項一覧(最重要)
│   ├── adr/
│   │   ├── 0001-...md ... 0045-...md
│   │   └── README.md                  # ADRインデックス(log4brains 風)
│   ├── specs/                         # arc42 のセクションに対応
│   │   ├── 01-introduction-and-goals/
│   │   ├── 03-context/
│   │   └── ...
│   └── _internal/
│       ├── README.md                  # _internal の目次
│       ├── AGENTS.md                  # Claude Code 向けの局所ガイド
│       ├── 00-overview/
│       ├── 10-runbooks/
│       ├── 20-onboarding/
│       └── 90-archive/                # 将来 deprecated 用

5.2 frontmatter スキーマ(推奨確定版)

---
type: adr | spec | runbook | guide | reference | onboarding
status: planned | draft | active | deprecated | superseded
                     # ADRの場合: planned | proposed | accepted | deprecated | superseded
audience: developer | operator | future-self
owner: "@kawaguchi"
created: 2026-05-15
updated: 2026-05-15
supersededBy: ADR-0046    # status: superseded のときのみ
planned_for: 2026-06-30    # status: planned のときのみ
---

5.3 GitHub Actions: orphan + frontmatter 検証

.github/workflows/docs-coverage.yml:

name: docs-coverage
on:
  pull_request:
    paths: ['docs/**', 'mkdocs.yml']
  push:
    branches: [main]
  schedule:
    - cron: '0 0 * * 1'   # 月曜0時に週次棚卸し

jobs:
  validate:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: actions/setup-python@v5
        with: { python-version: '3.12' }
      - run: pip install mkdocs python-frontmatter pyyaml

      # 1) orphan 検出 = mkdocs --strict
      - name: orphan check
        run: mkdocs build --strict

      # 2) frontmatter 必須項目検証
      - name: frontmatter schema check
        run: python scripts/check_frontmatter.py docs/

      # 3) status: planned スタブの賞味期限チェック
      - name: stale stub check
        run: python scripts/check_stale_stubs.py docs/ --days 30

scripts/check_frontmatter.py:

import sys, glob, frontmatter, pathlib
REQUIRED = {"type", "status", "audience", "owner"}
ALLOWED_STATUS = {"planned", "draft", "active", "deprecated", "superseded",
                  "proposed", "accepted"}  # ADR との互換
errors = 0
for path in glob.glob("docs/**/*.md", recursive=True):
    if pathlib.Path(path).name in ("README.md", "SUMMARY.md", "COVERAGE_GAPS.md"):
        continue
    meta, _ = frontmatter.parse(open(path).read())
    missing = REQUIRED - set(meta.keys())
    if missing:
        print(f"::error file={path}::missing frontmatter: {sorted(missing)}")
        errors += 1
    if meta.get("status") not in ALLOWED_STATUS:
        print(f"::error file={path}::invalid status: {meta.get('status')}")
        errors += 1
sys.exit(1 if errors else 0)

scripts/check_stale_stubs.py:

import sys, glob, subprocess, datetime, frontmatter, argparse
parser = argparse.ArgumentParser()
parser.add_argument("root")
parser.add_argument("--days", type=int, default=30)
args = parser.parse_args()
threshold = datetime.datetime.now() - datetime.timedelta(days=args.days)
stale = []
for path in glob.glob(f"{args.root}/**/*.md", recursive=True):
    meta, _ = frontmatter.parse(open(path).read())
    if meta.get("status") != "planned":
        continue
    out = subprocess.check_output(
        ["git", "log", "-1", "--format=%cI", path]).decode().strip()
    if not out:
        continue
    last = datetime.datetime.fromisoformat(out)
    if last.replace(tzinfo=None) < threshold:
        stale.append((path, last.date()))
if stale:
    print("::warning::stale planned stubs:")
    for p, d in stale:
        print(f"  {p}  (last touched {d})")
# 警告のみで CI は失敗させない(ソロ運用への配慮)
sys.exit(0)

5.4 CLAUDE.md / AGENTS.md(70行版)

# bizlp-gas-accounting — agent brief

## Stack
GAS V8 + Sheets + clasp + GitHub Actions + LangGraph TS on Cloudflare Workers

## Build / test
- `npm run lint` before commit
- `npm test` for unit tests
- `clasp push` deploys GAS (do NOT run autonomously)

## Documentation conventions
**IMPORTANT**: Every doc has YAML frontmatter with `status`. Treat them as:
- `planned`: stub, content NOT YET written → ask the user, do not infer
- `draft`: partial → verify with user before relying
- `active`: trusted
- `deprecated`: do not propose for new work
- `superseded`: follow `supersededBy` field

If you cannot find a doc on a topic, **say "no doc exists" — do NOT invent one**.
See `docs/COVERAGE_GAPS.md` for the known-unknowns list.

## Where things live
- `docs/adr/` — architecture decisions (45 ADRs, append-only)
- `docs/specs/` — arc42 structure (ADR-0039)
- `docs/_internal/` — runbooks, onboarding, internal ops (ADR-0045)
- `docs/COVERAGE_GAPS.md` — what is NOT yet documented

## Gotchas
- GAS V8 has no top-level await; use IIFE
- LangGraph TS state must be JSON-serializable for Workers KV
- clasp `.clasp.json` is gitignored — never commit OAuth tokens

5.5 COVERAGE_GAPS.md 運用

---
type: reference
status: active
audience: developer
owner: "@kawaguchi"
updated: 2026-05-15
---
# 既知のカバレッジギャップ

このファイルは「口頭で決まったが文書化されていないこと」「検討中で保留中のこと」を一覧化する。
Claude Code はこのファイルを参照し、ここに列挙された事項について質問されたら **ユーザーに確認** すること。

## 口頭決定(要文書化)
- [ ] エラー通知の Slack 投稿先チャンネル → `docs/_internal/10-runbooks/error-notification.md` に planned スタブあり
- [ ] 月次バックアップの保存期間 → ADR 候補

## 検討中・保留
- [ ] LangGraph の checkpoint storage を Workers KV にするか D1 にするか → ADR-0046 で扱う予定

5.6 6ヶ月後に再発しない仕組み

  1. 週次 cron: check_stale_stubs.py が GitHub Issue を自動 open(30日以上動かない planned スタブ)。
  2. PR テンプレート: 「このPRは新しい口頭決定を生んだか? Y/N」チェック欄。Y なら ADR or planned スタブ追加必須。
  3. 月次レビュー(5分で済む): Claude Code に 「COVERAGE_GAPS.md と全 status: planned ファイルを横断レビューし、コードと矛盾するものを指摘して」 を投げる。

5.7 移行コスト試算(Claude Code 活用前提)

タスク所要時間
frontmatter スキーマ確定(本レポートを叩き台に)30分
既存 230 本に Claude Code でバルク frontmatter 追加1〜2時間(Claude Code に一括指示)
GitHub Actions YAML + Python 2 スクリプト追加30分
CLAUDE.md / AGENTS.md / COVERAGE_GAPS.md 初版作成1時間
_internal/ を番号付きサブディレクトリへリパス1時間(Claude Code に git mv を一括指示)
合計半日(4〜5時間)

Recommendations(段階的導入ステップ)

Phase 1(半日、即実施推奨)

  1. frontmatter スキーマ確定(§5.2)
  2. CLAUDE.md / AGENTS.md / COVERAGE_GAPS.md の3ファイル作成
  3. Claude Code に「全 docs に frontmatter を一括付与」を指示

判断基準: Phase 1 完了後、「Claude Code に質問して、planned スタブの内容を捏造しなくなったか」を1週間モニター。捏造が続くなら CLAUDE.md の IMPORTANT 強調を増やす。

Phase 2(半日、Phase 1 から2週間後)

  1. GitHub Actions の docs-coverage workflow 追加
  2. check_frontmatter.py / check_stale_stubs.py 投入
  3. ADR フォーマットも MADR 4.0 に統一

判断基準: CI が PR を1〜2件ブロック(=実際に書き忘れが見つかった)したら成功。3週間鳴かなければルールが緩すぎる。

Phase 3(Jr. エンジニア参加直前)

  1. PR テンプレートに「口頭決定の有無」チェック欄追加
  2. needs-docs ラベル運用(GAS / LangGraph コード変更時に docs/ 変更がない場合)
  3. オンボーディングドキュメント(docs/_internal/20-onboarding/)の充実

判断基準: Jr. エンジニアが入って2週間後、「COVERAGE_GAPS.md を一度も見ずに作業を進めた回数」を計測。3回以上あれば CLAUDE.md のリンク導線を強化。

しきい値・閾値

  • CLAUDE.md / AGENTS.md が200行を超えたら: 子ファイルへリンクで逃がす(Anthropic 公式推奨上限)。
  • ADR が 100 本を超えたら: archived status を追加導入し、log4brains 等の専用ツール検討。
  • チームが 4 名を超えたら: 月次レビュー会を正式運用に格上げ。

Caveats(注意事項・反対意見)

  1. status enum を導入したが運用されない罠: Docusaurus が enum 案から boolean 2軸に収束した歴史が示す通り、enum は破綻しやすい。CI で必ず enum 値域を検証すること(§5.3 の check_frontmatter.py で実装済み)。
  2. AI エージェント向け「Anti-Patterns」セクションの逆効果: Augment Code のブログ記事(augmentcode.com/blog/how-to-write-good-agents-dot-md-files、2026年4月22日)は「Warning-only documentation consistently underperformed documentation that paired prohibitions with a concrete alternative」と警告。「これはやってはいけない」だけ書くと、エージェントは過剰に保守的になり、作業量が落ちる。必ず「代替の正しい行動」とセットで書くこと。
  3. LLM 生成の AGENTS.md は逆効果になりうる: ETH Zurich の論文「Evaluating AGENTS.md: Are Repository-Level Context Files Helpful for Coding Agents?」(arXiv:2602.11988、2026年2月13日)によれば、LLM 生成の context ファイルは SWE-bench Lite で -0.5 pp、AGENTbench で -2 pp の成功率低下、推論コスト +20〜23% 増という結果。Claude Code に CLAUDE.md を生成させる場合も、人間が必ず手動で枝刈り(pruning)すること
  4. SUMMARY.md の手動メンテナンスは破綻する: 150本のドキュメントを抱える bizlp では、mkdocs-literate-nav または自動生成スクリプト前提でないと SUMMARY.md は陳腐化する。
  5. status: planned スタブを Git で push してよいか: 個人ブランチで作って手元検討中、PR 経由でしか main に入らない運用なら問題ない。直接 push する場合は「planned が10件溜まったら警告」など追加の閾値が必要。
  6. arc42 の12セクションを全部埋めようとしない: Gernot Starke 自身が「The cabinet has a value, even if certain compartments remain empty」と述べる。ソロ運用なら 1, 3, 4, 5, 8, 9, 10 の7セクションで十分。
  7. 「Definition of Done に doc 更新を入れる」教義の限界: 大企業のスクラム文献では定番だが、ソロ運用では「DoD = 自分との約束」になり強制力ゼロ。強制力は CI に持たせるのが現実解。
  8. Diátaxis をトップダウンで導入しない: 公式自身が「don't try to work on the big picture」と警告。bizlp の 30本を一気に Diátaxis 4分類に分けるのではなく、新規ドキュメントから順次タグ付けする。

他モデルとの比較観点(Claude 固有の知見)

GPT-4o Deep Research や Gemini Deep Research が出力しがちな観点と、Claude として強調すべき点:

  1. 「進歩的開示(progressive disclosure)」の重視: AGENTS.md / CLAUDE.md は短く保ち、詳細は子ファイルへリンクする。HumanLayer・Anthropic 公式が一貫して主張。他モデルは「網羅性」を優先しがちで、CLAUDE.md を肥大化させる提案をすることがある。
  2. 不在の表明を許可する明示的設計: 「ファイルが見つからなければユーザーに聞く」という規約をドキュメント側に書く発想は、Anthropic 公式の reduce-hallucinations ガイダンスに直結する Claude 固有の系統。GPT / Gemini 系の解説は「frontmatter を充実させる」方向に偏りやすい。
  3. 「ベストプラクティス」の批判的検証: Augment Code のブログ記事や ETH Zurich の論文が示す逆風データを組み込む。他モデルはベストプラクティスを無批判に列挙しがち。
  4. ソロ開発の現実への適合: 「Definition of Done に doc 更新を入れる」「四半期レビューを持つ」といった企業ベストプラクティスはソロ運用では維持不能。本レポートは「週次 cron + Claude Code に投げる5分レビュー」という現実解を提案。
  5. arc42 と Diátaxis の役割分離: 一緒くたに語られがちだが、対象読者が異なる(arc42=アーキテクト、Diátaxis=ユーザー)。bizlp の _internal/ には Diátaxis のフラットなタグ運用が、docs/specs/ には arc42 のセクション構造が向く、という棲み分けを明示。
  6. 「意図的な未記録」を表現する手段: 「カバレッジ100%を目指す」というナイーブな提案ではなく、COVERAGE_GAPS.md という別ファイルで「未記録だが意図的」を表現する設計。これは Claude のように「不在を不在として認識する」訓練を受けたモデルが活きる仕組み。
  7. Append-only ADR の徹底: MADR / Nygard / log4brains が一致して主張する「Once accepted, ADR is immutable」という原則を、frontmatter の status 設計と CI ルールに落とし込む。
  8. 数値の出典明示: 「3% の成功率低下」「200行上限」といった具体的な数値を、ETH Zurich の arXiv 論文 (2602.11988)・Anthropic 公式ベストプラクティス(TurboDocx blog 引用)など named source で示す。他モデルは「研究によれば」程度の曖昧な引用で済ませがち。