# スペックアンカード開発

AIエージェントは、人間が手作業でドキュメントを正しく保てる速度を超えて
コードを書きます。Gurenの答えはひとつの原則です:

> **導出できるものは導出し、できないものは宣言し、常に検証する。**
> (Derived where possible, declared where not, checked always.)

- **導出(Derived)** — コードから証明できるものはコードから生成します。
  ER図、ドメインモデル、画面一覧、モジュールマップ、エンティティの
  完全なコンテキスト。
- **宣言(Declared)** — コードで表現できないものは書き残し、対象の
  コードへ明示的にリンクします。意思決定、ビジネスルール、背景。
- **検証(Checked)** — どちらも機械的に検証されます。古くなった生成
  ビューや切れたdocリンクは、コードレビューではなくチェックが落とします。

その結果、コードが動いても嘘をつかない仕様が手に入ります — あなたに
とっても、リポジトリで作業するすべてのエージェントにとっても。

## 導出: スペックビュー

```bash
bunx guren spec:generate
```

は `docs/spec/` に4つのMarkdownビューを生成します。それぞれが1つの
問いに答えます:

| ファイル | 答える問い |
|------|--------------------|
| `er.md` | データベースはどんな形か? `db/schema.ts` 由来のMermaid ER図 — カラム・型・キー、エッジはモデルのリレーション宣言から |
| `domain.md` | ドメインオブジェクトは何か? モジュールごとにグループ化したモデルのクラス図(カーディナリティ付き) |
| `screens.md` | 各画面は何を受け取るか? ページ → Props型 → それを描画するルート |
| `modules.md` | アプリはどう分割されているか? モジュール・所属モデル・モジュール間依存 |

出力は決定的で、コード変更なしの再生成はバイト単位で一致します。
だからファイルはコミットされ、PRのdiffが「その変更が仕様に何をしたか」
をそのまま見せます。手で編集してはいけません — 信頼を人に頼らないため
のドリフトゲートがあります:

```bash
bunx guren check --spec    # メモリ内で再生成し、ドリフトがあれば非ゼロexit
```

## 導出: エンティティコンテキスト

```bash
bunx guren context User
```

は1つのモデルについてプロジェクトが知るすべてを結合します — テーブルと
カラム、双方向のリレーション、バリデーションスキーマ付きのルート、
コントローラのアクション、Props付きInertiaページ、Resource、Policy、
ファクトリ、シーダー、テスト、そして紐付いたドキュメント。エージェント
向けには `--json`、同名モデルは `--module <name>` で解決します
(`--module app` はアプリルートを指します)。MCP接続エージェントには
`guren_entity_context` ツールとして同じバンドルが提供されます。

## 宣言: ドキュメントとコードの紐付け

意思決定やビジネス背景は `docs/`(および `modules/<name>/docs/`)配下の
Markdownとして残します。frontmatterが「この文書が何を統べるか」を宣言します:

```yaml
---
kind: adr
status: accepted
entities: [Invoice]
related:
  - app/Http/Controllers/InvoiceController.ts
  - modules/billing/**
last_reviewed: 2026-07-25
---
```

- `entities` はモデルのクラス名でリンクします — `bunx guren context Invoice`
  が、次にそのモデルを触る誰かにこの文書を提示します。
- `related` はモデル以外のコードを統べる文書のためのファイル/globリンクです。
- モデルとコントローラからは JSDoc タグで逆リンクを張れます:
  `/** @docs docs/adr/0001-billing.md */`(それ以外のファイルのタグは走査されません)

意思決定はジェネレータで記録します:

```bash
bunx guren make:adr "Billing cycle is end-of-month" --entity Invoice
```

`docs/adr/` 配下に採番されたファイルを作り、frontmatterを記入済みに
します。`--entity` は既存のコードから `entities:` と `related:` を
自動補完します。新規Gurenアプリには、この規約を説明するシードADRが
最初から同梱されています。

## 検証: ゲート

`bunx guren check` は、route/controller/pageの整合性チェックと並んで、
切れたdocリンク(リネームされた `related` パス、存在しなくなった
エンティティ、宛先を失った `@docs` タグ)と古くなったスペックビューを
報告します。プレーンなコマンドは情報提供で、CIをゲートする(非ゼロexit)
のはスイートフラグです:

```bash
bunx guren check --docs    # docリンクのみ
bunx guren check --spec    # スペックドリフトのみ
bunx guren check --arch    # アーキテクチャ境界のみ
```

docs/specのチェックはどちらもコンテンツ起動です: `docs/` も
`docs/spec/` も `@docs` タグもなければ結果ゼロなので、規約を採用する
まで何も赤くなりません。`check --changed`(エージェントハーネスの
edit hookがルート・コントローラ・モデル・スキーマ・ページの編集後に
実行するモード)では、検証はその変更が影響しうる範囲に絞られ、ループは
高速なままです。CIではフルのゲートが走ります。

## なぜエージェントに効くのか

古いドキュメントは、AIエージェントにとって「ないより悪い」存在です —
エージェントは嘘を全幅の信頼で読みます。導出ビューはコードから再生成
され、宣言リンクはcheckスイートが検証するので、`bunx guren context Invoice`
を実行したエージェントが得るコンテキストは「リンクと導出ビューは検証済み
だとチェッカーが確認したもの」です(本文の鮮度は別軸のオプトイン警告で、
`check --docs --docs-ttl <days>` が `last_reviewed` の古い文書を指摘
します)。新規アプリのエージェントハーネスはこのループを
教えます — モデルに触る前にエンティティコンテキストを引く、ファイルを
動かしたらfrontmatterも同じ変更で更新する、構造を変えたらスペックビュー
を再生成する — そしてedit hookがそれを機械的に強制します。

## 次のステップ

- [Why Guren](./why-guren.md) — フレームワークのエージェントネイティブ設計における位置づけ。
- [CLIリファレンス](./cli.md) — 全コマンド・フラグ・CIでの使い方。
- [アーキテクチャ](./architecture.md) — 導出ビューの土台になっている規約。
