mcpField
G
gecko-mcp

gecko-mcp

ローカル
github.com/Frumaneブラウザ自動化219 週間前に更新

gecko-mcp について

gecko-mcpは、FloorpやFirefox系ブラウザーの実セッションを操作するMCPサーバーです。ページの読み取り、タブ管理、スクリーンショット、操作機能を備え、OS入力とページJavaScriptの実行は有効化するまでロックされています。

主な機能

  1. 01MarkdownまたはHTMLでページを読み取り
  2. 02タブの一覧表示、作成、移動、終了
  3. 03ページ要素の検索と操作
  4. 04表示領域またはページ全体の撮影
  5. 05任意で使えるOS入力とJavaScriptツール

活用シーン

  1. 01ログイン中のブラウザーでページ内容を確認
  2. 02タブ移動やフォーム入力を自動化
  3. 03ブラウザー作業のスクリーンショットを撮影

MCP 対応

MCPクライアントにページ読み取り、タブ管理、撮影、操作ツールを提供します。Floorpの組み込みAPIまたはMarionette経由でGeckoブラウザーに接続します。

設定

ローカルサーバーの設定はどのクライアントでも共通です。コピーしてクライアントの MCP 設定ファイルに貼り付けてください。

mcp.json · 共通設定
{
"mcpServers": {
"frumane-gecko": {
"command": "npx",
"args": [
"-y",
"gecko-mcp"
]
}
}
}
起動コマンドnpx -y gecko-mcp

ローカルサーバーにはマシン上の実行環境(Node.js 18 以上など)が必要です。設定ファイルの場所はクライアントごとに異なります。

パッケージ
npmgecko-mcp2.2.4

ツール

41

掲載時のツール一覧 · 2 週間前に更新

このツールにパラメーターはありません。

詳細

gecko-mcp

CI License: MIT

MCP(Model Context Protocol) サーバーです。Claude Code、 Claude Desktop、Cursor、あらゆる MCP クライアントなどの AI アシスタントが、 実際にログインしたセッションを使って、Floorp やその他の Firefox ベースのブラウザー (LibreWolf、Waterfox、Zen、Mullvad、Firefox など)でページの読み取り、スクリーンショットの撮影、タブの管理を行えます。

「Chrome の Claude」のようなものですが、Firefox/Gecko 系全体に対応しています。

gecko-mcp 経由で Floorp を操作する Claude — 自然言語のプロンプトから GitHub リポジトリと npm のページを開くデモ

約30秒で始められます:

npx gecko-mcp setup

gecko-mcp を Claude Code、Claude Desktop、Cursor、VS Code(Copilot)、Windsurf、Zed、Codex などに登録します。プロジェクト単位でも全体でも設定できます。手動設定についてはセットアップ、ブラウザーで一度だけ行う手順については要件をご覧ください。

インストールに不安がありますか? その慎重さは大切です。これは小規模(依存関係は2つで、すべて src/ 内にあります)で、OS のキーボード/マウス操作はデフォルトでロックされています(許可するまではブラウザー内のみ)。 リリースにはnpm provenance(ソースと照合可能)が付属し、完全な脅威モデルは SECURITY.md に記載されています。npx gecko-mcp を実行する前にお読みください。

仕組み

gecko-mcp は、次の2つのバックエンドのいずれかを自動選択してブラウザーと通信します。

  • Floorp には、自動化用の HTTP API が組み込まれています。about:config で floorp.mcp.enabled = true に設定すると、gecko-mcp は高速な http://127.0.0.1:58261 API を使用します。 拡張機能は不要で、最も豊富な機能を利用できます。
  • その他の Gecko ブラウザー — Firefox 派生ブラウザーすべてに組み込まれている自動化 エンジン、Marionette を使って起動すると、gecko-mcp はライブセッションを 操作します。同じツールを、同じ実際のセッションで利用できます。
  Claude Code / Desktop / Cursor
            │  MCP (stdio)
            ▼
      gecko-mcp ──► Floorp :58261 (built-in API)        ─┐
   (this project) ──► Marionette :2828 (any Gecko fork)  ─┴─► your real tabs

要件

  • 自動化が有効になっている Firefox ベースのブラウザーがインストールされ、実行中であること:
    • Floorp: about:config で floorp.mcp.enabled を true に設定し、Floorp を再起動します。
    • その他の派生ブラウザー(LibreWolf/Waterfox/Zen/Mullvad/Firefox): ブラウザーを -marionette を付けて起動します(ブラウザーのサポートをご覧ください)。
  • Node.js ≥ 18。

セットアップ

クイックスタート — セットアップウィザード
npx gecko-mcp setup

対話型ウィザードで、お好みの AI コーディングツール(Claude Code、Cursor、Windsurf、VS Code(Copilot)、Gemini CLI、Codex、 Zed、Cline。または Kimi Code、Antigravity など、その他の MCP クライアント用のコピー&ペーストできる設定スニペット)に gecko-mcp を登録し、 現在のプロジェクトまたは**グローバル(すべてのリポジトリ)**にインストールできます。既存の設定にマージし、先にバックアップを作成します。

非対話型/スクリプトからの実行:

npx gecko-mcp setup --list                          # show supported tools
npx gecko-mcp setup --tool claude-code,cursor --scope global
npx gecko-mcp setup --tool codex --scope global --print   # dry run
手動設定

このサーバーブロックを使えば、どの MCP クライアントでも利用できます(リポジトリのクローンやビルドは不要です。npx が取得します)。

{
  "mcpServers": {
    "gecko": {
      "command": "npx",
      "args": ["-y", "gecko-mcp"]
    }
  }
}

または、Claude Code の CLI を使います:claude mcp add gecko -s user -- npx -y gecko-mcp。

Floorp で一度だけ行う手順: about:config で floorp.mcp.enabled = true に設定し、 Floorp を再起動して、自動化 API を利用できるようにします。

ブラウザーのサポート

gecko-mcp はバックエンドを自動的に選択します。Floorp の :58261 API に接続できる場合はそれを使用し、接続できない場合は、すべての Gecko ブラウザーに組み込まれている自動化エンジン Marionette に接続します。Floorp 以外のブラウザーを使うには、Marionette を有効にして一度起動します。

ブラウザーMarionette を有効にして起動
Floorp(フラグは不要です。floorp.mcp.enabled=true を設定するだけで、ネイティブ API が使用されます)
Firefoxfirefox -marionette
LibreWolflibrewolf -marionette
Waterfoxwaterfox -marionette
Zenzen -marionette
Mullvadmullvad-browser -marionette

Marionette はデフォルトで TCP 2828 をリッスンします。別のポートを使うには、プロファイル内の marionette.port 設定値(たとえば user.js 経由)を変更し、一致する MARIONETTE_PORT を指定して gecko-mcp を起動します。GECKO_MCP_BACKEND=marionette を設定すると、バックエンドを強制できます。

注: 実行中のセッションに接続するには、起動時に Marionette を有効にする必要があります。 Marionette バックエンドでは、Floorp 専用の追加機能(snapshot のフィンガープリント、 list_workspaces/switch_workspace、アクセシビリティツリー)は「サポートされていません」という明確なメッセージを返します。その場合は、 代わりに find/read_page を使用してください。それ以外の機能 (タブ、ナビゲーション、クリック、入力、フォーム、スクリーンショット、Cookie、実際の OS 入力など)はすべて動作します。

ツール

タブと読み取り

ツール機能
list_tabs開いているすべてのタブを一覧表示します(タイトル、URL、browserId、アクティブ状態、ピン留め状態)。
open_tabURL を指定して新しいタブを開きます。新しいタブの browserId が返されるため、そのタブを対象に操作できます。
get_active_tabアクティブなタブのタイトル、URL、browserId を返します。
navigate_tab既存のタブを指定した URL に移動します。
close_tabタブを閉じます。
read_pageタブの内容をクリーンな Markdown(または HTML/アクセシビリティツリー)として読み取ります。コンテキストを保護するため、出力には上限(デフォルト 25 KB)が設定されています。
find高速な要素ロケーター — 表示テキストやタグを使ってページをサーバー側で検索し、HTML 全体ではなく、すぐに使える CSS selector の簡潔な一覧(約 1 KB)を返します。ボタン/リンク/フィールドを探し、返されたセレクターを使って操作します。
snapshot構造化されたページマップです。インラインの fp: 参照を含む Markdown と要素セレクターのマップを返します。HTML を検索せずに要素を特定し、ref を使って操作できます。
screenshotタブのスクリーンショットを撮影します(ビューポートまたはページ全体)。
launch_floorpFloorp が実行中であることを確認し、API に接続できない場合は起動します(Windows)。
launchMarionette を有効にして、任意の Firefox ベースのブラウザー(Firefox、LibreWolf、Zen など)を起動し、gecko-mcp から操作できるようにします。

操作

ツール機能
clickCSS セレクターまたは snapshot の ref で要素をクリックします。クリック前に自動的に要素を画面内へスクロールします。
type_textCSS セレクターで、入力欄/テキストエリア、またはリッチテキスト/contenteditable エディター(Slate、ProseMirror など)にテキストを入力します。
fill_form複数のフィールドに一度に入力します。
press_keyキーボードのキー(Enter、Tab など)を押します。
wait_for_element要素が DOM に追加される、表示されるなどの状態になるまで待機します。
get_value機密情報を扱います。 入力欄/テキストエリア/セレクトの現在値を読み取ります(パスワード欄も読み取ることができます)。

ほとんどのツールはデフォルトでアクティブなタブを対象にします。特定のタブを対象にするには、browserId(list_tabs で取得)を渡します。

OS キーボードとマウス — デフォルトでロックされています 🔒

以下のツールはブラウザーの外部に影響を与える可能性があるため、有効にするまで無効になっています。何も設定しない場合、gecko-mcp はブラウザーの自動化のみを行います。「OS 入力を有効にして」と依頼するだけでセッションごとにロックを解除できます(enable_os_input ツールが呼び出されます)。または、GECKO_MCP_ENABLE_OS_INPUT=1 で永続的に有効にできます。disable_os_input で再びロックします。ロック中にこれらのツールを呼び出すと、明確なメッセージを表示して拒否します。

evaluate ツール(任意のページ JavaScript を実行)も同様にロックされています。enable_evaluate または GECKO_MCP_ENABLE_EVALUATE=1 でロックを解除できます。

ツール機能
enable_os_input / disable_os_inputこのセッションで OS キーボードとマウスのツールのロックを解除/再度ロックします。
enable_evaluate / disable_evaluateこのセッションで evaluate(ページ JS を実行)ツールのロックを解除/再度ロックします。
evaluateロックされています。 ページで JavaScript を実行し、その値を返します(return …)。

実際の OS キーボード(Windows) — React/リッチテキストエディターや、合成入力を無視するボット対策付きの送信操作向けです。

ツール機能
real_type本物の OS キーイベント(isTrusted)を使って、フォーカス中の要素に入力します。
real_key"Enter"、"ctrl+a" などの実際のキー/キーの組み合わせを押します。
real_clear実際の Ctrl+A と Delete を実行します。リッチテキスト/contenteditable フィールドを確実にクリアします。

これらはページから人間の入力と区別できない入力を生成するため、合成クリックや入力では操作できない React/Slate エディターや送信入力欄を操作できます。ワークフロー:入力欄を click してフォーカスし、続けて real_clear/real_type/real_key "Enter" を実行します。

安全ガード: OS のキー入力はフォアグラウンドのウィンドウに送られるため、これらのツールは入力を送る前に Floorp をフォアグラウンドに表示し、検証します。Floorp が起動していない、またはフォーカスできない場合、キーを一度も入力せずに中止するため、入力が別のアプリに漏れることはありません。

実際の OS マウス(Windows) — 画面座標を指定して、本物の isTrusted クリックを行います。

ツール機能
window_boundsFloorp のウィンドウの画面ピクセル上の矩形(対象位置の計算に使用)。
move_cursor実際の OS カーソルを Floorp 内の画面ピクセル位置に移動します。
real_clickFloorp 内の画面ピクセル位置で実際の OS クリック(左/右、シングル/ダブル)を行います。

二重ガード: クリックは Floorp がフォアグラウンドにあると検証され、かつ座標が Floorp のウィンドウ矩形内にある場合にのみ送信されます。誤った座標は拒否されるため、別のアプリ/ウィンドウがクリックされることはありません。座標は画面ピクセル単位です(スクリーンショットから座標を特定する場合は、ディスプレイの拡大率/DPI に注意してください)。

その他の操作とクエリ

ツール機能
hover / double_click / right_click要素(セレクターまたは ref)に対するマウス操作。
select_option<select> のオプションを選択します。
set_checkedチェックボックスまたはラジオボタンのオン/オフを切り替えます。
submit_formフォームを送信します。
upload_file機密性の高い操作です。 絶対パスでファイル <input> にファイルを設定します。GECKO_MCP_ALLOW_UPLOAD_DIRS で制限できます。
get_attribute要素の属性(href、value など)を読み取ります。
get_articleReadability で抽出したメイン記事を Markdown として読み取ります。
get_cookies機密性の高い操作です。 ページから参照できる Cookie を取得します。includeValues: true を指定しない限り、値は伏せられます。
wait_for_network_idleネットワークの動作が落ち着くまで待ちます。
list_workspaces / switch_workspaceFloorp のワークスペース(対応している場合)。

セキュリティ

有効にする前に、脅威モデルを理解してください。主なリスクは 2 つあります。

  1. Floorp の自動化 API は、デフォルトでは認証されません。
    floorp.mcp.enabled がオンになっている間は、あらゆるローカルプロセスが 127.0.0.1:58261 経由でログイン済みブラウザーを操作できます。このサーバーに限りません。また、Origin のチェックがないため、悪意のあるウェブページが CSRF/DNS リバインディングを試みる可能性もあります。対策:

    • 自動化を使っていないときは、floorp.mcp.enabled をオフにします。
    • GECKO_MCP_TOKEN 環境変数を設定すると、このサーバーはすべてのリクエストに Bearer トークンを付加します(トークンを強制する Floorp ビルドでは有効で、それ以外では影響ありません)。
  2. プロンプトインジェクション(「致命的な三要素」)。 アシスタントは信頼できないページのコンテンツを読み取り、さらに認証済みセッション上で操作(クリック、入力、送信、移動、実際の OS 入力)できます。悪意のあるページが、アシスタントをあなたに不利な操作へ誘導しようとする可能性があります。ページから読み取ったものはすべて信頼できないものとして扱い、信頼していないサイトでは自動化を無人で実行しないでください。

このサーバーに組み込まれているセキュリティ強化策:

  • OS のキーボード/マウス操作はデフォルトでロックされています(最小権限): ブラウザーの外部で操作できるツールは、明示的にロックを解除するまで実行を拒否します(enable_os_input ツール、または GECKO_MCP_ENABLE_OS_INPUT=1)。デフォルトでは、gecko-mcp が自動化できるのはブラウザーだけで、マシン全体を操作することはありません。
  • 実際の OS 入力には二重のガードがあります: キー/クリックの送信前に Floorp がフォアグラウンドウィンドウであることを確認し、マウスクリックが Floorp ウィンドウの矩形内に着地する必要があります。そうでない場合は、何も送信せずに中止します。PowerShell のペイロードは、プロセス専用の環境変数を介して Base64 エンコードで渡されます(シェルによる展開なし、ディスク上に一時スクリプトファイルを作成しません)。
  • URL スキームとホストの許可リスト: デフォルトでは、open_tab/navigate_tab が受け付けるのは http(s)(および about:blank)のみで、ループバック/プライベートホスト(127.0.0.1、localhost、10/8、172.16/12、192.168/16、169.254/16、IPv6 ULA/リンクローカル)へのアクセスは拒否されます。これにより、プロンプトインジェクションされたエージェントがブラウザーの移動先を Floorp 自身の API や LAN に切り替え、応答を読み取るのを防ぎます。GECKO_MCP_ALLOW_PRIVILEGED_URLS=1 で解除できます。必要に応じて、GECKO_MCP_ALLOW_DOMAINS で移動先をドメインの許可リストに限定できます。
  • get_cookies では、デフォルトで Cookie の値が伏せられます。 生の値を取得するには、明示的に includeValues: true を指定する必要があります。
  • get_value はシークレットを読み取る可能性があります: ブラウザーでは同一オリジンの JS がパスワードフィールドを読み取れるため、このツールは入力済みのパスワードを返すことがあります。SENSITIVE としてフラグ付けされています。ユーザーから指定されたフィールドに限って使用し、認証情報の収集には決して使用しないでください。
  • アップロードの許可リスト: GECKO_MCP_ALLOW_UPLOAD_DIRS(ディレクトリを ; で区切る)を設定すると、upload_file が指定ディレクトリ内に制限されます。パスは realpath で正規化(シンボリックリンクを解決)され、..、シンボリックリンク、同じプレフィックスを持つ隣接ディレクトリ、または UNC パスによって許可されたフォルダーの外に出られないよう検証されます。
  • find は非表示要素をスキップします(インラインの display:none/visibility:hidden、hidden、type=hidden、aria-hidden)。これにより、ページ上のテキスト検索を使って、非表示のボタンをクリックするようエージェントを誘導できないようにします。
  • 入力の上限: 数値/テキストのツールパラメーターには範囲と長さの上限が設定されています(座標、タイムアウト、maxChars、find の上限、入力テキスト、フォームフィールド)。リソース枯渇やクラッシュを引き起こす入力を防ぐためです。
  • API エラーの切り詰めとポートの検証: Floorp のエラーボディーはモデルに渡す前に切り詰められます。GECKO_MCP_PORT は 1~65535 の範囲で検証されます。
  • 人間の確認を介在させるためのツールアノテーション: すべてのツールには MCP ヒント(readOnlyHint/destructiveHint/…)が付いているため、クライアントは読み取り専用ツールを自動実行し、破壊的な操作(close_tab、navigate_tab、submit_form、upload_file)について確認できます。サーバーは独自にプロンプトを表示できません。承認はクライアントの役割です。これにより gecko-mcp は、何が安全で何が重大な操作かをクライアントに伝えます。
  • evaluate ツールはありません: 任意のページ JS の実行は、意図的に公開していません。 防御されないもの(固有の制限/Floorp 側の制限):悪意のあるローカルプロセスは、認証されていないループバック API(平文、TLS なし)を引き続き読み取ったり、なりすましたりできます。また、自動化対象として選んだページからのプロンプトインジェクションによって、そのページ上の正規の操作が実行される可能性があります。アイドル時は floorp.mcp.enabled を無効にし、信頼できないサイトを無人で自動化しないでください。
環境変数効果
GECKO_MCP_TOKENAuthorization: Bearer … として Floorp API に送信されます。
GECKO_MCP_PORTAPI ポート(デフォルトは 58261、有効範囲は 1~65535)。
GECKO_MCP_ALLOW_PRIVILEGED_URLS1 にすると、open/navigate で非 http(s) URL およびループバック/プライベートホストを許可します。
GECKO_MCP_ALLOW_DOMAINSナビゲーションで許可するドメインのカンマ区切りリスト(サブドメインを含む)。未設定の場合は、すべてのパブリックホストを許可します。
GECKO_MCP_ALLOW_UPLOAD_DIRSupload_file の対象をこれらのディレクトリに制限します(; 区切り)。
FLOORP_PATHlaunch_floorp 用の floorp.exe のフルパス。
GECKO_MCP_BACKENDバックエンドを強制指定します:floorp または marionette。デフォルト:自動検出。
MARIONETTE_PORTFloorp 以外のブラウザー用 Marionette TCP ポート(デフォルトは 2828)。
GECKO_MCP_ENABLE_OS_INPUT1 にすると、起動時に OS キーボード/マウスツールのロックを解除します(それ以外の場合は、enable_os_input ツールが呼び出されるまでロックされます)。
GECKO_MCP_ENABLE_EVALUATE1 にすると、起動時に evaluate(ページ JS を実行)ツールのロックを解除します(それ以外の場合は、enable_evaluate が呼び出されるまでロックされます)。
GECKO_MCP_BROWSER_PROCESS実際の OS キーボード/マウスで操作対象にできるプロセス名の正規表現(デフォルトでは一般的な Gecko 派生ブラウザーに対応します)。

旧形式の FLOORP_MCP_* 変数名も引き続きフォールバックとして機能するため(名称変更前の設定との互換性のため)、既存の設定は引き続き動作します。今後は GECKO_MCP_* を使用してください。

パフォーマンス

  • HTTP ツール呼び出しの負荷は軽微です — Floorp のローカル API に対する attach → act → detach の一連の処理は約 5~6 ms です。find はページ上をサーバー側で検索し、HTML 全体を出力する代わりに、そのまま使えるセレクターを約 1 KB 返します。また、read_page には上限(デフォルト 25 KB)があるため、ページの読み取りでコンテキストがあふれることはありません。
  • 実際の OS 入力には、永続的な PowerShell ホストを使用します。 powershell.exe の起動(約 700 ms)と P/Invoke ヘルパーのコンパイル(約 600 ms)は、以前は呼び出しごと(real_*/move_cursor/window_bounds、それぞれ約 1.9 s)に発生していました。現在はホストを必要に応じて 1 つ起動し、コンパイルを一度だけ行って読み取り・評価ループを実行するため、初回の呼び出しには約 1.6 s かかりますが、その後の呼び出しは、ガード付きのキー入力/クリックなら約 350 ms(約 5 倍高速)、ウィンドウ境界の照会なら数 ms です。フォアグラウンド/境界の安全ガードはすべてのコマンドで引き続き実行され、ホストがハングしたり終了したりした場合は再起動されます。

注意事項と制限

実際のアプリ(Google Flow など)を操作して得られた知見:

  • リッチエディター: type_text は通常の入力欄と contenteditable エディター(Slate、ProseMirror、Lexical)の両方に対応しています。要素に .value がない場合は、実際のテキスト入力イベントのディスパッチに切り替えます。このようなエディターを確実にクリアする方法は、まだ解決されていません(select-all/evaluate がありません)。
  • React の入力欄の送信: 多くのチャット/プロンプト入力欄は、送信ボタンの合成クリックではなく、実際の Enter キーの keydown で送信されます。その場合は click ではなく、press_key "Enter" を使用してください。
  • 信頼できるイベント: ページ JavaScript から isTrusted=true を偽造することはできません。これはブラウザーのセキュリティ不変条件です。Floorp は特権レイヤーで入力を注入するため、通常のクリック/キー入力は実際の操作と同様に動作します。ただし、reCAPTCHA や厳格なボット検出で保護されたワークフローでは、自動送信が拒否される場合があります。
  • evaluate: 一部の Floorp ビルドではページ JS の eval エンドポイントが HTTP 404 を返すため、ここではツールとして公開していません。
  • 複数ウィンドウ: 複数のウィンドウが開いている場合、「アクティブなタブ」は曖昧になります(各ウィンドウにそれぞれアクティブなタブがあるためです)。open_tab が返す browserId、または list_tabs で取得した browserId を使用し、すべてのツールに明示的に渡してください。

ロードマップ

  • タブ管理、ページの読み取り、スクリーンショット
  • 操作ツール:クリック、入力、フォームへの入力、キー押下、フィールド値の読み取り
  • 実 OS キーボード(Windows):real_type / real_key / real_clear。フォアグラウンド安全ガードを備え、React/Slate エディターとボットガード付き送信を操作します
  • snapshot(フィンガープリント参照とセレクターマップ)+ref による click +表示位置への自動スクロール
  • launch_floorp — Floorp が起動していない場合に起動します(Windows)
  • 追加ツール:ホバー、ダブルクリック/右クリック、select_option、set_checked、submit、 upload_file、get_attribute、get_article、get_cookies、wait_for_network_idle、workspaces
  • 実 OS マウス(Windows):window_bounds / move_cursor / real_click。フォアグラウンドとウィンドウ内の境界を二重に確認します
  • Marionette バックエンド — すべての Firefox ベースのブラウザー(LibreWolf、Waterfox、 Zen、Mullvad、Firefox など)。Floorp の API がない場合に自動選択されます
  • macOS / Linux のネイティブ入力バックエンド
  • JavaScript の evaluate(新しい Floorp ビルドでは利用可能です。古いビルドでは HTTP 404 が返されます)
  • オプションのベアラートークン認証
  • Floorp 以外のブラウザー向け launch ヘルパー(-marionette を付けて起動します)

謝辞

Floorp が公開している自動化 API を基に構築されています。公式の Floorp-Projects/floorp-mcp-server は、エンドポイントの対応関係を調べるうえで参考になりました。これは独立してクリーンルーム方式で実装された、MIT ライセンスのプロジェクトです。

ライセンス

MIT © Frumane

コメント

MCP は初めてですか?

プロトコルの概要から最初のサーバーの導入まで、よくある疑問にまとめて答えます。

AI アプリケーションが外部のツールやデータソースに統一的な方法で接続するためのオープンなプロトコルです。クライアントはモデルとの対話を担い、MCP サーバーはツール・リソース・プロンプトテンプレートを提供します。標準メッセージでやり取りするため、1 つのサーバーを複数のクライアントで再利用できます。