AIエージェント入門

マルチエージェントAI設計パターン4選|Python実装ガイド

マルチエージェントAI設計パターン4選|Python実装ガイド

この記事の結論

マルチエージェントAIの4つのオーケストレーションパターンをPythonコード付きで解説。GitHubが公開した失敗回避の設計原則も紹介。

結論: マルチエージェントAIシステムの成否を決めるのはモデル性能ではなく、エージェント間の「オーケストレーション設計」である。

▶ 関連記事:A2Aプロトコルとは?マルチエージェント連携の標準規格を解説

この記事の要点:

  • 要点1: マルチエージェントには4つの基本パターン(Supervisor / Router / Hierarchical / Swarm)があり、用途で使い分ける
  • 要点2: GitHubの調査によると、失敗の大半は「構造の欠如」が原因であり、型付きスキーマとアクションスキーマで解決できる
  • 要点3: PythonとLangGraphで、今日から動くマルチエージェントシステムを構築できる

対象読者: シングルエージェントは構築済みで、複数エージェントの連携に挑戦したいエンジニア・PM

読了後にできること: LangGraphでSupervisorパターンのマルチエージェントを実装し、ローカルで動かす

「AIエージェントを1つ作ったけど、複数を連携させると途端に崩壊する…」

▶ 関連記事:AIエージェントとは?基礎から仕組み・活用事例まで解説

これは多くの開発チームが直面する壁です。シングルエージェントなら安定して動くのに、2つ以上のエージェントが協調し始めると、タスクの重複、矛盾する出力、無限ループといった問題が頻発します。

GitHub Blogが2026年2月に公開した記事「Multi-agent workflows often fail」では、この原因を明確に指摘しています。エージェントの失敗はモデル性能ではなく、構造の欠如――つまりオーケストレーション設計の問題だと。

この記事では、マルチエージェントの4つのオーケストレーションパターンを、コピペ可能なPythonコード付きで解説します。5分で動くサンプルから始めましょう。

まず試したい「5分即効」セットアップ

以下のコードで、最もシンプルなSupervisorパターンのマルチエージェントを動かせます。

# 動作環境: Python 3.11+, langgraph>=0.3.0, langchain-openai>=0.3.0
# pip install langgraph langchain-openai langchain-core
import os
from langchain_openai import ChatOpenAI
from langgraph.graph import StateGraph, MessagesState, START, END

os.environ["OPENAI_API_KEY"] = os.getenv("OPENAI_API_KEY", "your-key")

llm = ChatOpenAI(model="gpt-4o")

# リサーチャーエージェント
def researcher(state: MessagesState):
    system = "あなたはリサーチ担当です。与えられたトピックについて要点を3つ挙げてください。"
    response = llm.invoke([{"role": "system", "content": system}] + state["messages"])
    return {"messages": [response]}

# ライターエージェント
def writer(state: MessagesState):
    system = "あなたはライター担当です。リサーチ結果をもとに、200字以内の要約を書いてください。"
    response = llm.invoke([{"role": "system", "content": system}] + state["messages"])
    return {"messages": [response]}

# グラフ構築
graph = StateGraph(MessagesState)
graph.add_node("researcher", researcher)
graph.add_node("writer", writer)
graph.add_edge(START, "researcher")
graph.add_edge("researcher", "writer")
graph.add_edge("writer", END)

app = graph.compile()
result = app.invoke({"messages": [{"role": "user", "content": "AIエージェントの最新トレンド"}]})
print(result["messages"][-1].content)
# 注意: 本番環境で使用する前に、必ずテスト環境で動作確認してください。

ポイント: このコードは直列パイプライン(Researcher → Writer)ですが、これがマルチエージェントの最小単位です。ここから条件分岐やループを加えることで、本格的なオーケストレーションに発展させます。

4つのオーケストレーションパターンを理解する

マルチエージェントの設計は、大きく4つのパターンに分類できます。用途と複雑度に応じて選択してください。

パターン 概要 適用場面 複雑度
Supervisor 1つの管理エージェントがタスクを分解・委任 CSボット、ドキュメント生成 ★★☆☆☆
Router 入力の種類に応じて専門エージェントに振り分け 問い合わせ分類、マルチスキル対応 ★★☆☆☆
Hierarchical Supervisorを階層化し、大規模タスクを分割統治 企業の部門横断ワークフロー ★★★★☆
Swarm エージェント同士が対等に協調・ハンドオフ 創造的タスク、ディベート ★★★☆☆

パターン1: Supervisor(最も実用的)

1つの「司令塔」エージェントが全体を統括し、専門エージェントにタスクを割り振るパターンです。Amazon Bedrockのマルチエージェントコラボレーションでも、このSupervisorモードがデフォルトとして採用されています。

# Supervisorパターン — 動的にエージェントを選択
# 動作環境: Python 3.11+, langgraph>=0.3.0
from typing import Literal
from langgraph.graph import StateGraph, MessagesState, START, END

def supervisor(state: MessagesState) -> dict:
    """タスク内容を判定し、適切なエージェントにルーティング"""
    last_msg = state["messages"][-1].content.lower()
    if "コード" in last_msg or "実装" in last_msg:
        return {"next": "coder"}
    elif "調査" in last_msg or "リサーチ" in last_msg:
        return {"next": "researcher"}
    else:
        return {"next": "writer"}

def route(state: dict) -> Literal["coder", "researcher", "writer"]:
    return state.get("next", "writer")

graph = StateGraph(MessagesState)
graph.add_node("supervisor", supervisor)
graph.add_node("coder", coder_agent)      # 各エージェント関数は別途定義
graph.add_node("researcher", researcher_agent)
graph.add_node("writer", writer_agent)
graph.add_conditional_edges("supervisor", route)
graph.add_edge(START, "supervisor")
for node in ["coder", "researcher", "writer"]:
    graph.add_edge(node, END)
app = graph.compile()

パターン2: Router(高速振り分け)

Supervisorがタスクを分解するのに対し、Routerは入力をそのまま最適なエージェントに転送します。タスク分解が不要な場合、Routerの方がレイテンシもコストも低くなります。

パターン3: Hierarchical(大規模向け)

Supervisorを入れ子にするパターンです。「経営企画Supervisor → マーケSupervisor → コンテンツAgent / 広告Agent」のように、組織構造をそのままエージェント階層に写像できます。

パターン4: Swarm(対等協調)

OpenAIのSwarmフレームワークで注目されたパターンです。中央の管理者を置かず、エージェント同士が直接ハンドオフします。柔軟性は高いですが、デバッグが難しくなるため、明確なハンドオフルールの設定が必須です。

GitHubが教える「失敗しない」3つの設計原則

GitHubは社内のCopilotやCI/CD自動化でマルチエージェントを大規模運用しており、2026年2月のブログで3つの設計原則を公開しました。

原則1: 型付きスキーマで曖昧さを排除する

エージェント間でやり取りするデータには、必ず型定義を設けます。自然言語のまま受け渡すと、フィールド名のブレや型の不一致で下流が壊れます。

# Pydanticでエージェント間のデータ契約を定義
# 動作環境: Python 3.11+, pydantic>=2.0
from pydantic import BaseModel, Field
from typing import Literal

class ResearchResult(BaseModel):
    """リサーチエージェントの出力スキーマ"""
    topic: str = Field(description="調査トピック")
    key_findings: list[str] = Field(description="主要な発見(3〜5件)")
    sources: list[str] = Field(description="参照ソースURL")
    confidence: Literal["high", "medium", "low"] = Field(description="情報の確信度")

class ActionDecision(BaseModel):
    """Supervisorのアクション決定スキーマ"""
    action_type: Literal["delegate", "respond", "escalate"] = Field(description="次のアクション")
    target_agent: str | None = Field(default=None, description="委任先エージェント名")
    reason: str = Field(description="判断理由")
# 注意: 本番環境で使用する前に、必ずテスト環境で動作確認してください。

ポイント: スキーマ違反は「契約違反」として即座にリトライまたはエスカレーションします。ログから原因を推測する必要がなくなります。

原則2: アクションスキーマで意図を明確にする

「この課題を分析して対応して」という曖昧な指示では、エージェントごとに異なる行動を取ります。許可するアクションを明示的に列挙することで、予測可能な動作を保証します。

原則3: MCPで構造を強制する

Model Context Protocol(MCP)は、ツール呼び出しの入出力スキーマを定義し、実行前にバリデーションを行います。スキーマとアクションの設計を「お約束」から「強制」に昇格させるのがMCPの役割です。

【要注意】よくある失敗パターンと回避策

失敗1: エージェント間で状態が共有されない

❌ 各エージェントが独立してLLMを呼び出し、前のエージェントの出力を参照しない
⭕ StateGraphの共有ステートに結果を書き込み、後続エージェントが参照する構造にする

なぜ重要か: あるエージェントが開いたIssueを、別のエージェントが重複と判断して閉じる――GitHubが実際に報告した典型的な失敗です。

失敗2: 無限ループに陥る

❌ エージェント同士が互いにタスクを投げ合い、終了条件がない
⭕ ループ回数の上限を設定し、上限に達したら人間にエスカレーションする

# ループ上限の設定例
MAX_ITERATIONS = 5
def should_continue(state: dict) -> str:
    if state.get("iteration_count", 0) >= MAX_ITERATIONS:
        return "escalate_to_human"
    return "continue"

失敗3: 全てのタスクをマルチエージェントにする

❌ シンプルなタスクにも複数エージェントを投入し、複雑性とコストが増大
⭕ まずシングルエージェントで解決できないか検討し、本当に分業が必要な場合のみマルチエージェントを採用する

なぜ重要か: エージェントを増やすほどレイテンシとAPI コストが増加します。2エージェントで済むところを5エージェントにしても、品質は上がりません。

失敗4: エラーハンドリングがない

❌ 1つのエージェントが失敗すると、パイプライン全体が停止
⭕ 各エージェントにtry/exceptとフォールバック処理を実装し、障害を局所化する

パターン選定フローチャート

どのパターンを選ぶべきか迷ったら、以下の判断基準を参考にしてください。

判断基準 推奨パターン 理由
タスクが明確に分業できる Supervisor 各エージェントの責務が明確になる
入力タイプで処理が分岐する Router 分類→転送のシンプルな構造で十分
組織の階層構造を反映したい Hierarchical 部門ごとのSupervisorで管理範囲を限定
創造的タスク・議論が必要 Swarm 対等な立場での多角的な検討が可能
タスクがシンプル シングルエージェント マルチエージェントは過剰設計

セキュリティと運用の注意点

マルチエージェントシステムでは、単一エージェント以上にセキュリティリスクが増大します。Adversa AIが2026年3月に公開したレポートでは、エージェント間通信における新たな攻撃面(間接的プロンプトインジェクション、エージェント間のペイロード汚染)が指摘されています。

  • プロンプトインジェクション対策: エージェント間で渡すデータは、必ず型付きスキーマでバリデーションし、自然言語の生テキストをそのまま次のエージェントに渡さない
  • APIキー管理: 各エージェントが個別にAPIキーをハードコードしない。環境変数またはSecrets Managerを使用する
  • コスト上限: マルチエージェントはAPI呼び出し回数が乗算的に増える。1リクエストあたりのトークン上限とループ回数上限を必ず設定する
  • ログとモニタリング: 各エージェントの入出力をログに記録し、異常な出力パターンを検知するアラートを設定する

正直にお伝えすると、マルチエージェントシステムの本番運用はまだ発展途上です。完璧な自律動作を期待するのではなく、人間がモニタリングし介入できる「Human-in-the-Loop」設計が現時点でのベストプラクティスです。

参考・出典

あわせて読みたいMastra TypeScript AIフレームワーク完全ガイド

あわせて読みたいOpenAI Agents SDK実践ガイド

まとめ:今日から始める3つのアクション

  1. 今日やること: 冒頭の「5分即効セットアップ」コードをコピペして、Researcher→Writerの直列パイプラインを動かしてみる
  2. 今週中: 自分の業務で「2つ以上のステップに分解できるタスク」を1つ選び、Supervisorパターンで試作する
  3. 今月中: 型付きスキーマ(Pydantic)とエラーハンドリングを追加し、チーム内でデモを実施する

あわせて読みたい:


著者: 佐藤傑(さとう・すぐる)
株式会社Uravation代表取締役。X(@SuguruKun_ai)フォロワー10万人超。
100社以上の企業向けAI研修・導入支援。著書累計3万部突破。
SoftBank IT連載7回執筆(NewsPicks最大1,125ピックス)。

ご質問・ご相談は お問い合わせフォーム からお気軽にどうぞ。

Need help moving from reading to rollout?

この記事を読んで導入イメージが固まってきた方へ

Uravationでは、AIエージェントの要件整理、PoC設計、社内導入、研修まで一気通貫で支援しています。

この記事をシェア

X Facebook LINE

※ 本記事の情報は2026年3月時点のものです。サービスの料金・仕様は変更される可能性があります。最新情報は各サービスの公式サイトをご確認ください。

関連記事