LLM がツールを直接呼び出す(MCP)
tools/war3_mcp.py は MCP サーバーです。Claude Code、Claude Desktop、または MCP に対応した任意のクライアントに登録すれば、LLM がコードを書かずに、局面を見る、コマンドを出す、画面上でプレイヤーに話しかける、カードを出してプレイヤーに尋ねる、スクリーンショットで画面を見る、といったことを直接行えます。
tools/war3_mcp.py は MCP サーバー(stdio)です。Claude Code、Claude Desktop、ローカルモデル用の Agent フレームワーク —— MCP に対応した任意のクライアントに登録すれば、LLM がコードを書かずに直接、局面を見る、コマンドを出す、ゲーム画面上でプレイヤーに話しかける、プレイヤーに尋ねる、スクリーンショットで画面を見る、といったことができます。
Bot を書く、アドバイザーを務める、ユニットにしゃべらせる、に続くもう 1 つの接続方法です:LLM 自身がツールの使い手になります。
登録する
claude mcp add war3 -- python <リポジトリ>\tools\war3_mcp.py --inst 9 # Claude Code。<リポジトリ> は自分の openwar3 フォルダに置き換える
他のクライアントでは、次の形式で設定を書きます。
{"mcpServers": {"war3": {"command": "python", "args": ["<リポジトリ>\\tools\\war3_mcp.py", "--inst", "9"]}}}
ゲームに接続するのは最初にツールが呼ばれたときなので、ゲームは後から起動しても構いません。ゲームを閉じて起動し直した場合も、次の呼び出しで自動的に再接続します。--role を付けると、LLM にできることを制限できます。
| ロール | 使えるもの |
|---|---|
dev(デフォルト) | すべてのツール。war3_jass を含む |
player --player N | N 番プレイヤーのユニットだけを指揮でき、その視界内のものだけが見えます(フェアモード)。JASS はなし |
observer | 読み取り専用。画面への描画も、ユニットにしゃべらせることもできない。下したコマンドはランタイムがそのまま拒否 |
player ロールの制限はゲートウェイと同じです:ゲームの終了、速度変更、一時停止は使えず、他プレイヤーの手の内が見える API も使えません。プレイヤー番号を取るクエリは自分の分しか照会できません。
いくつかの上限:1 つのツール結果は最大 20 万文字で、超えた分は切り詰められ、範囲の絞り方が示されます。war3_ask_player の待ち時間は最大 120 秒です。スクリーンショットの scale は 0.1 から 1 の間です。
ツール
| ツール | 内容 |
|---|---|
war3_overview | 局面の要約:時刻、資源、人口、自軍の兵種ごとの数、ヒーロー(HP、マナ、レベル、クールダウン)、見えている敵の兵種、生産。最初にこれを呼ぶ |
war3_units | ユニット一覧(owner は me / enemy / creep / all、types で絞り込み)。コマンドを出すときは addr を使う |
war3_events | 前回の呼び出し以降に起きたこと:死亡、レベルアップ、スキル使用、生産完了、チャット、プレイヤーがボタンをクリック……(デフォルトでは大量に流れる数種類を除外) |
war3_call | 任意の公開 API を呼ぶ(move、attack_move、train、build、cast、learn、ui.button、canvas.text……)。ユニットは {"unit": addr} で指定 |
war3_api | API を調べる:キーワードで名前と説明を検索 |
war3_toast / war3_say | 画面上部に 1 行のテキスト / ユニットの頭上にひと言 |
war3_ask_player | 画面中央にプレイヤー向けの選択カードを数枚出し、クリックを待って、どれが選ばれたかを返す(ゲームを一時停止できる) |
war3_screenshot | ゲーム画面のスクリーンショット(PNG。ウィンドウが隠れていても撮れて、フォーカスも奪わない) |
war3_jass | JASS を実行(dev 専用。ワールドを変更できるのはシングルプレイのみ) |
こんな使い方ができます:
- 一緒に遊ぶ / コーチ:
war3_overviewで局面を見て、war3_toastで画面にアドバイスを出す。 - プレイしながらプレイヤーに尋ねる:
war3_ask_playerでカードを 3 枚出し、プレイヤーが選んだとおりに進める。 - 実況:
war3_eventsで何が起きたかを読み、war3_sayでユニット自身にしゃべらせる。 - 1 つの部隊を直接指揮する:
playerロール +war3_callで、自分のユニットだけを動かす。 - 画面を見て UI を調整する:
war3_screenshotで 1 枚撮り、自分で描いたボタンの配置が正しいかを確認する。
会話はたとえばこんな感じ
あなた:今の局面を見て、それから画面で聞いて:次は拡張、兵の量産、ティアアップのどれにする?
→ war3_overview {}
← 局面の要約:ゲーム時間、ゴールド 500、人口 10/12、自軍 htow 1 · hpea 5 · Hpal 1、敵は見えず、生産中のものなし
→ war3_ask_player {"question": "次はどうする?", "options": ["兵の量産", "拡張", "ティアアップ"], "pause": true}
← {"picked": 1, "option": "拡張"}
モデル:拡張を選びましたね。まず war3_units で手の空いている農民を探し、最寄りの金鉱がどこかを確認します……
実測
2026-09-25:
- 自作の MCP クライアントを実際の試合につないで 7/7:ハンドシェイク → ツール一覧(10 個)→
war3_overview(htow1、hpea5)→war3_units→war3_toast→war3_screenshot(PNG 約 20 万バイト)→war3_ask_player(カード 3 枚。2 枚目のクリックをシミュレート →{"picked": 1, "option": "拡張"})。 - Claude Code 2.1 に実際に登録:Claude Code が自分でサーバーを起動してハンドシェイクし、ステータスは
connected。10 個のツールがすべてmcp__war3__*としてツール一覧に現れました。
実装
- 改行区切りの JSON-RPC 2.0(
initialize/tools/list/tools/call/ping)。プロトコルバージョンは 2025-06-18 で、2025-03-26 と 2024-11-05 にも対応します。 - ツールのエラーは MCP の規約どおり結果の中に入れ(
isError: true)、接続は切りません。 - ゲートウェイ と、同じロールのホワイトリスト、ユニット引数の形式、「局面の要約」を共有しています。
- ログは stderr に出し、stdout にはプロトコルだけを流します。