はじめに
前回の第1章では、**Model Context Protocol(MCP)**の概要を紹介し、AIを外部データやツールと接続する「USB-Cのような標準化プロトコル」としてその重要性を説明しました。今回は、MCPがどのように動作するのか、技術的な仕組みを掘り下げます。クライアント-サーバーアーキテクチャ、JSON-RPCベースの通信、そしてMCPの主要コンポーネントについて詳しく解説します。開発者にとって、MCPの実装イメージを具体化できる内容を目指します。
この記事を読み終える頃には、MCPの内部構造を理解し、実際に自分で試してみるための基礎知識が得られるはずです。さっそく見ていきましょう!
MCPのアーキテクチャ:全体像
MCPは、クライアント-サーバーモデルに基づいて設計されています。以下は、MCPの主要な構成要素です:
-
MCP Host
- ユーザーが直接操作するアプリケーション(例:Claude Desktop、IDE、チャットボット)。
- Hostは、AIモデル(LLM)と対話し、ユーザーのリクエストを処理します。
-
MCP Client
- HostとServerの間を取り持つ中間層。
- Clientは、HostからのリクエストをServerに転送し、結果を返します。1:1の安全な通信を保証します。
-
MCP Server
- 外部データやツールを提供するエンドポイント(例:Google Drive、GitHub、データベース)。
- Serverは、リソースやツールをAIに提供し、必要に応じてアクションを実行します。
このアーキテクチャは、シンプルかつスケーラブルです。たとえば、IDEがHost、ClaudeがClient、GitHubがServerとして連携するシナリオを想像してください。IDE内でコード補完を求めると、ClaudeがGitHubのリポジトリデータを取得し、適切な提案を返します。
MCPの動作フロー
MCPは、JSON-RPC 2.0をベースにした通信プロトコルを使用します。以下は、MCPの基本的な動作ステップです:
-
初期化(Initialization)
- HostがClientに接続し、通信セッションを開始。
- 認証(例:OAuth 2.1)が行われ、安全性が確保される。
-
機能探索(Discovery)
- ClientがServerに「どんなリソースやツールを提供できる?」と問い合わせ。
- Serverは、利用可能なリソースやツールのリストを返答。
-
コンテキスト提供(Context Provision)
- Serverがリソース(例:ファイル、データベース)やツール(例:API呼び出し)をAIに提供。
- AIはこれを使って、ユーザーのリクエストに応じた回答やアクションを生成。
このプロセスは、HTTPのようなリクエスト-レスポンスモデルに似ていますが、AIのニーズに特化して最適化されています。
MCPの3つの主要コンポーネント
MCPの強力さは、以下の3つのコンポーネントにあります:
1. リソース(Resources)
- 定義:AIに提供される静的なデータ(例:ファイル、データベース、ドキュメント)。
-
例:プロジェクトの
README.md
や、PostgreSQLのテーブルスキーマ。 - 用途:AIがコンテキストを理解し、より正確な回答を生成するために使用。
2. ツール(Tools)
- 定義:AIが実行できる関数やAPI(例:メール送信、データベース更新)。
- 例:GitHub APIを呼び出してプルリクエストを作成。
- 用途:AIがユーザーの指示に基づいてアクションを実行。
3. プロンプト(Prompts)
- 定義:AIがリソースやツールを効果的に使うためのガイドラインやテンプレート。
- 例:「このデータベーススキーマを基に、効率的なSELECTクエリを提案してください」。
- 用途:AIの出力をユーザーの意図に合わせる。
これら3つが連携することで、MCPはAIを単なるテキスト生成機から、データ駆動型のアシスタントに変えます。
セキュリティ:MCPの安全性の確保
MCPは、セキュリティを最優先に設計されています。主なセキュリティ機能は以下の通りです:
- OAuth 2.1認証:ユーザーの認証情報を安全に管理。
- 細かなアクセス制御:リソースごとに読み取り専用(read-only)や破壊的(destructive)な操作を制限。
- ユーザー同意:ツールが実行される前に、ユーザーの明示的な許可が必要。
- 暗号化:通信はHTTPSを介して行われ、データ漏洩を防止。
たとえば、Google Driveに接続する場合、ユーザーはまずGoogleアカウントでログインし、MCPがどのフォルダにアクセスできるかを明示的に指定します。これにより、意図しないデータアクセスが防がれます。
コード例:シンプルなMCPサーバーの実装
MCPの動作を具体化するために、Pythonを使った簡単なMCPサーバーの例を示します。このサーバーは、ディレクトリ内のファイルリストをリソースとして提供します。
from mcp import MCPServer
import os
class SimpleFileServer(MCPServer):
def __init__(self, host, port):
super().__init__(host, port)
self.register_resource("list_files", self.list_files)
def list_files(self, params):
directory = params.get("directory", ".")
try:
files = os.listdir(directory)
return {"status": "success", "files": files}
except Exception as e:
return {"status": "error", "message": str(e)}
if __name__ == "__main__":
server = SimpleFileServer(host="localhost", port=8080)
print("Starting MCP Server on localhost:8080...")
server.start()
コードの説明
- MCPServer:MCPの基本クラスで、JSON-RPC通信を処理。
- list_files:指定ディレクトリのファイルリストを返すリソース。
- register_resource:このメソッドでリソースを登録し、AIがアクセス可能に。
- start():サーバーを起動し、Clientからのリクエストを待機。
このサーバーを起動すると、Claude Desktopや他のMCP対応アプリケーションからlist_files
リソースにアクセスできます。たとえば、以下のようなJSON-RPCリクエストが送信されます:
{
"jsonrpc": "2.0",
"method": "list_files",
"params": {"directory": "/path/to/folder"},
"id": 1
}
レスポンス例:
{
"jsonrpc": "2.0",
"result": {
"status": "success",
"files": ["file1.txt", "file2.py"]
},
"id": 1
}
このシンプルな例でも、MCPがデータ提供をどのように標準化するかがわかります。
実際の応用例
MCPの仕組みを理解したところで、実際のシナリオを見てみましょう:
シナリオ:IDEでのコード補完
- 環境:Zed Editor(MCP対応)+PostgreSQLデータベース。
-
フロー:
- ZedがMCP Clientとして、PostgreSQL用のMCP Serverに接続。
- Serverがデータベースのスキーマ(テーブル、列情報)をリソースとして提供。
- ユーザーが「SELECT * FROM ...」と入力すると、AIがスキーマを参照し、正確なSQLクエリを提案。
- 利点:カスタムプラグインを書くことなく、AIがデータベースのコンテキストを即座に理解。
このように、MCPは開発プロセスを劇的に効率化します。
まとめと次へのステップ
この第2章では、MCPのクライアント-サーバーアーキテクチャ、JSON-RPCベースの通信、そしてリソース・ツール・プロンプトの3つのコンポーネントを解説しました。MCPは、シンプルさと柔軟性を両立させ、AIを外部データやツールと安全に接続するための基盤を提供します。
次の第3章では、「MCPの実装方法」をテーマに、実際にMCPサーバーを構築し、Claude DesktopやIDEに統合する手順を紹介します。コードを書きながら学びたい方は、ぜひお楽しみに!
役に立ったと思ったら、「いいね」や「ストック」をしていただけると嬉しいです!次の章でまたお会いしましょう!