Spec-Driven Developmentとは何か?仕様を信頼の源(Source of Truth)とする

仕様書こそが唯一の信頼情報源であり、単なる補助文書ではない。

目次

仕様駆動型開発(Spec-Driven Development)は、ソフトウェアエンジニアが以前から追求してきたものの、努力に見合う成果が得られなくなった際に棚上げされてきたアイデアの一つです。

2025年に変化したのは、AIコーディングエージェントが登場し、明示的な意図の欠如がコストとして課せられるようになったことです。プロンプトは一過性のものです。エージェントのセッションはリセットされ、コードは変更されますが、その背後にある推論は消えてしまいます。仕様(Spec)は、そのような事態を防ぐためのアーティファクト(成果物)なのです。

仕様駆動型開発とは – AIコーディングにおける真の源泉としての仕様

仕様が「真の源泉(Source of Truth)」になりつつある

ソフトウェア開発の歴史の大部分において、仕様は一時の計画用アーティファクトか、あるいは後から考えられたことにすぎませんでした。要件はチケットに、設計上の決定はチャットスレッドに保管され、コードこそが真の源泉(ground truth)でした。ドキュメントは、事実として存在するものを記述するものでした。

仕様駆動型開発(SDD)は、この関係を逆転させます。仕様が一次のアーティファクトとなります。コードは仕様に従って生成されるか、仕様に対して検証されるものであり、その逆ではありません。

これは新しいアイデアではありません。形式手法、契約による設計、BDD(行動駆動型開発)には、そのバージョンが含まれています。新しいのは実用的な動機です。AIコーディングエージェントは、正しく一貫した出力を生成するためには、明示的で耐久性のあるコンテキストを必要とします。プロンプトは一過性すぎて不十分です。エージェントのセッション間、チームメンバー間、そして時間を超えて意図を運ぶことができるのは、仕様というアーティファクトだけです。

仕様駆動型開発が実際に意味すること

通常SDDと略される仕様駆動型開発とは、バージョン管理された仕様が実装をガイドするか、あるいは生成するワークフローです。エージェントがコードを書く前に、仕様は記述され、レビューされます。そこには以下の要素が含まれます。

  • 何を構築するか – ユーザーの問題、目標、および非目標(non-goals)
  • 正しい振る舞いとは何か – 受け入れ基準、エッジケース、エラー状態
  • どのように構築するか – アーキテクチャの決定、データモデル、API契約、セキュリティ制約
  • どのように検証するか – テスト戦略、検証ルール、要件へのトレーサビリティ

仕様は一度きりのドキュメントではありません。現実が設計と異なる場合は更新されます。エージェントが実装中に仕様では誤っていたと判断される発見をした場合、作業を続ける前に仕様が修正されます。仕様はコードのように扱われるため、誠実さを保ちます。

最近の学術的な取り組みはこの枠組みを形式化しています。研究者らはSDDを、仕様を真の源泉とし、コードをそれに対して生成または検証するものとして記述しています。実用的な解釈では、仕様は人間やAIツールが読み取り、信頼できる、レビュー済みで耐久性のある意図の記録です。

次の3つの用語は、仕様の利用における異なる立場を表しています。

**Spec-first(仕様ファースト)**とは、実装を開始する前に完全な仕様を書くことを意味します。これは最も厳格な解釈であり、注意深く行われない場合、ウォーターフォール型に近いものです。

**Spec-anchored(仕様アンカー)**とは、機能のライフサイクル全体を通じて、仕様を実装と同期させることを意味します。決定が変更されるにつれて、仕様は更新されます。これは多くのチームにとって最も実用的なバージョンです。

**Spec-as-source(仕様としての源泉)**とは、仕様から実装を生成するか、AIエージェントやツールを用いてコードが仕様の制約に対してチェックされることを意味します。GitHub Spec KitやKiroなどのツールはこの方向性へ進んでいます。

なぜ今、SDDが重要なのか

正直な答えは、SDDは1日限りのスクリプトを構築する単独の開発者には魅力的ではないということです。オーバーヘッドに見合う価値がありません。

SDDが価値を持つのは、以下の3つの条件が揃った場合です。機能が複数のセッションにまたがるほど大規模であり、エージェントがアーキテクチャに影響を与える決定を行う必要があり、作業が他の人によってレビューされ、あるいは継続される場合です。

AI支援開発において、この3つの条件はますます一般的になっています。

LLMはコンテキストを必要とし、プロンプトだけでは不十分です。 曖昧なプロンプトを受け取るモデルは、曖昧な決定を下します。明示的な制約、非目標、受け入れ基準を備えたレビュー済み仕様を受け取るモデルは、より良い決定を下し、軌道を逸れたときに軌道修正が容易になります。これは、知識管理における検索と表現の仕組みと関連しています。エージェントにバージョン管理された仕様を提供することは、プロジェクトの意図を構造化した検索の一種です。

コード生成は安価ですが、何を構築するかの決定は依然として困難です。 AI支援開発におけるボトルネックは、もはやタイピングではありません。何を構築し、エージェントをどのように制約するかを知ることです。SDDは、その労力を重要度が高い箇所へシフトさせます。生成が開始される前に、意図を明確に指定することです。

プロンプトは一過性です。 エージェントは、前回のセッションで指示したことを記憶していません。リポジトリに保存されたバージョン管理された仕様は記憶しています。新しいセッションはすべて同じ仕様を読み取り、コンテキストを一から再構築することなく、同じ意図に対して実装できます。

Vibe Codingは、機能している間だけ有効です。 プロトタイプや使い捨ての作業では、アドホックなプロンプトの方が速く、適切です。しかし、機能にセキュリティ制約、マルチファイルアーキテクチャの決定、またはチーム間の手引きが必要になった瞬間、仕様の欠如がドリフト(逸脱)と欠陥の主な原因となります。各アプローチが適用される時期については、SDDとVibe Codingの比較をご覧ください。

コアアーティファクト

実用的なSDDワークフローは、4つの主要なアーティファクトを生成します。それぞれがエージェントに到達する前に、特定の種類の曖昧さを減らします。

要件仕様。 問題記述、影響を受けるユーザー、目標、明示的な非目標、および受け入れ基準です。非目標は目標と同様に重要です – それらはエージェントに何を作らないかを伝え、スコープの蔓延を防ぎます。受け入れ基準は、それぞれが少なくとも1つのテストに対応するほど明確です。

設計仕様。 この機能に関連するアーキテクチャの決定:影響を受けるモジュール、データモデルの変更、API契約、マイグレーション、セキュリティ制約、観測性(Observability)要件、および既知の失敗モードです。これは完全なシステム設計ドキュメントではありません – この機能を正しく実装するために必要なアーキテクチャ決定のサブセットです。

タスクプラン。 明示的な依存関係、期待されるファイル変更、および検証基準を備えた小さな実装タスクのシーケンスです。タスクは、単一のエージェントセッションで実装し、焦点を絞ったdiffで検証できるほど小さくします。各タスクには人間のレビューチェックポイントがあります。

トレーサビリティ記録。 受け入れ基準からテストへ、設計決定から影響を受けるファイルへ、タスクからコミットへのマッピングです。これはSDDを陳腐化するドキュメントから区別するものです。トレーサビリティにより、仕様が実際に実装されたか、単に書かれただけかを検証可能になります。

これらのアーティファクトは heavyweight(大規模・重厚)である必要はありません。単純な機能では、4つの領域をすべてカバーする単一の2ページ分のMarkdownドキュメントが生成されるかもしれません。フォーマットよりも、実装が開始される前に意図を書き留める習慣の方が重要です。

SDDがドキュメントと異なる点

最も一般的な誤解は、SDDアーティファクトをドキュメントとして扱うことです。それらは従来の意味でのドキュメントではありません。

ドキュメントは記述します。 システムが何をするか、どのように使用するか、そして何を含んでいるかを伝えます。それは事後的に書かれ、システムが変更された際に更新されます。

仕様は制約します。 仕様は、エージェントが構築することを許可されているものと、許可されていないものを伝えます。実装が開始される前に権威があります。実装が完了した後に検証されます。実際に構築されたものを記述する仕様 – 構築すべきものを制約するのではなく – は、すでにその役割を果たしていません。

実行可能な仕様は生成と検証をガイドします。 最善のSDD仕様は、エージェントがそれに対して実装でき、テストスイートが検証できるほど機械可读性(machine-readable)に近いです。「エンドポイントは認証されていないリクエストを401レスポンスで拒否しなければならない」という受け入れ基準は実行可能な仕様です。「エンドポイントはセキュアである」という記述はドキュメントです。

意思決定記録 – ADR、PDR、DDR – はSDDアーティファクトを補完しますが、異なる目的を果たします。意思決定記録は、なぜ選択が行われ、何が却下されたかを記録します。SDD仕様は、何を構築し、どのように検証するかを記録します。両者はリポジトリに属します。これらを合わせることで、AIエージェントは現在の意図とその背後にある推論という完全な図像を得ることができます。

SDDがTDDと異なる点

テスト駆動型開発(TDD)と仕様駆動型開発(SDD)は、どちらもコードが存在する前に明示的なアーティファクトを生成するため、混同されがちです。違いは出発点にあります。

TDDはテストから始まります。 望む振る舞いを記述する失敗するテストを書き、次にそれをパスさせるための最小限のコードを書きます。TDDはユニットレベルでのフィードバックループです。良いテストを生み出しますが、「正しいものを構築しているか」という問いには答えません。

SDDは意図から始まります。 テストが存在する前に、アーキテクチャが決定される前に、仕様は次の問いに答えます。誰がこの問題を抱えているか、正しい振る舞いとは何か、明確に範囲外なのは何か。仕様は次にどのテストを書くべきかを informs(通知・影響)し、それが良いSDDと良いTDDが競争するのではなく補完的なものである理由です。

それを考える実用的な方法:SDDがTDDを駆動します。仕様内の受け入れ基準がテストシナリオになります。設計仕様は、契約テストが必要な統合境界を特定します。タスクプランは、エージェントがそれを実装する前に、テストカバレッジが必要なユニット振る舞いを特定します。

SDDがBDDと異なる点

行動駆動型開発(BDD)は、自然言語のシナリオ – 通常Gherkin形式 – を使用して、ユーザーの視点からの期待される振る舞いを記述します。これらのシナリオは、ビジネスの意図と技術的な実装の間のギャップを埋めます。

SDDはより広範です。振る舞いの記述(BDDスタイルの言語または通常の散文を使用可能)を含みますが、アーキテクチャの決定、データモデル、セキュリティ制約、タスクプランニング、トレーサビリティもカバーします。BDDは、SDD要件仕様内で受け入れ基準を書くための有用なフォーマットとなり得ます。仕様がコンテナであり、BDDシナリオはそこに何を記述するかを示す一つの方法です。

この違いは実際には重要です。BDDツールはシナリオを実行可能にすることに焦点を当てています。SDDの実践は、ツールを超え、セッションを超え、チームメンバーを超えて意図を耐久性のあるものすることに焦点を当てています。

SDDが形式手法と異なる点

形式手法は、数学的な記法と自動検証を使用して、ソフトウェアシステムのプロパティを証明します。それらは非常に厳密であり、ほとんどの本番開発環境において非常にコストがかかります。

SDDは形式記法を必要としません。受け入れ基準とアーキテクチャの決定を含むMarkdownファイルは仕様です。それは数学的に形式的ではないものの、制約を設けます。厳密さのレベルは賭けられているものの大きさに応じて変化します:請求サービスのための仕様は、ドキュメントページのための仕様よりも、より正確で注意深くレビューされるべきです。

その関係はスペクトル(連続体)です:

  • 非公式の散文仕様(最小限のSDD)
  • 受け入れ基準と非目標を含む構造化されたMarkdown
  • スキーマ検証を備えた機械可读仕様
  • 仕様から直接派生した契約テスト
  • 自動証明を備えた形式的仕様

ほとんどのチームはこのスペクトルの中間で運用しています。目標は数学的な厳密さではありません。AIエージェントがそれに対して実装でき、人間のレビューアーが結果を検証できるほど、意図を明示的にすることです。

仕様駆動型開発の利点

意図のドリフト(逸脱)の減少。 仕様は基準となります。エージェントが逸脱した場合 – 必ずそうなります – レビューアーは実装と比較するためのものを持っています。仕様なしでは、何かが壊れるまでドリフトは目に見えません。

より良いAI出力。 明示的な制約、非目標、および受け入れ基準を与えられたエージェントは、意図されたものに近い実装を生成し、見逃した場合でも修正が容易になります。コンテキストの品質が直接出力の品質を決定します。

容易なレビュー。 仕様に関連付けられたプルリクエストは、レビューアーがコードから意図を再構築することを要求するプルリクエストよりもレビューが容易です。仕様はレビューチェックリストです。

チームの整合性。 複数の人またはエージェントが同じ機能に取り組んでいる場合、仕様は共有契約です。それなしでは、各貢献者がローカル最適化を行い、部品が適合しない可能性があります。

より良いテスト計画。 仕様内の受け入れ基準はテストケースに直接マッピングされます。テストカバレッジは仕様カバレッジの問題になります:すべての受け入れ基準が少なくとも1つのテストでカバーされているか?

耐久性のある手引き。 機能が手渡される場合 – エンジニア間、エージェントセッション間、スプリント間 – 仕様は手引きのアーティファクトです。何が決定され、何が範囲外であり、何がまだ検証されるべきかを記録します。

仕様駆動型開発のコスト

前倒しの努力。 どのコードも書く前に良い仕様を書くには時間がかかります。小さな機能では、このオーバーヘッドは現実のもので、時に見合う価値がありません。

偽の自信。 存在するが実装に対して検証されていない仕様は、正しさという偽の感覚を与えます。陳腐化した仕様は、それがない場合よりも悪く、レビューアーやそれを読むエージェントを誤らせます。

陳腐化した仕様。 チームが仕書を計画用アーティファクトとしてではなく、生きているドキュメントとして扱わない場合、仕様は逸脱します。実装が設計と異なる場合に仕様を更新することはオプションではありません – それは、蓄積して腐敗するドキュメントからSDDを区別するものです。

生成された官僚主義。 AIエージェントは、包括的なタスクリストと冗長な仕様を迅速に生成できます。30秒で生成された200タスクの仕様は有用な仕様ではありません – それは官僚主義ジェネレーターです。良いSDDには、何を指定し、何を暗黙のままにするかについての判断が必要です。

ツールへのロックイン。 一部のSDDツールは、フォーマット、ファイル構造、ワークフローについて意見が分かれています。プロプリエタリなフォーマットで書かれた仕様は、明確なヘッダーと受け入れ基準を持つMarkdownファイルよりも、ツール間で持ち運びにくいです。

結論

仕様駆動型開発は新しい方法論ではありません。暗黙的な意図のコストが、AI生成コードにおいて可視化されたため、実用的になった古き良き規律です。

その規律はシンプルです。エージェントがそれを構築する前に、構築しようとする意図をレビュー済みでバージョン管理された形で書き留めます。現実に違いがある場合にそれを更新し、その記録を誠実なものに保ちます。それをレビュー、テスト、手引きの基準として使用します。

仕様は魔法ではありません。検証されない仕様は、最も高価な種類のドキュメントになります:自信を持って誤導するものです。良いSDDは、仕様を誠実な状態に保つ実践です – 維持できるほど小さく、制約できるほど正確で、単一のエージェントセッションを超えて耐久できるほどです。

SDDは、ドキュメントの実践、テストアーキテクチャ、コード設計の交差点に位置します – これらはすべて、意思決定記録、API設計、データアクセスポターンと一緒に、App Architecture in Productionクラスターでカバーされています。

有用なリンク

購読する

システム、インフラ、AIエンジニアリングの新記事をお届けします。