gmail-mcp
あなたのAIアシスタントのためのGmail — 複数のアカウントを同時に、あなた自身のサーバーで。
gmail-mcp は、Gmail を Claude やその他の MCP クライアントに接続します。検索・読み取り、引用履歴付きの送信・全員返信、転送、添付ファイルやインライン画像の処理、下書き・ラベル・スレッドの管理を、複数の Google アカウントで同時に行えます。
これはあなた自身の Cloudflare Worker 上のリモートサーバーとして動作するため、同じ接続がノートPCの Claude Code、ブラウザの claude.ai、スマホの Claude から応答します。各接続は1つの Google アカウントにサインインし、Google のリフレッシュトークンはあなたの Cloudflare アカウントに保持されます。
ここに来る理由は2つあります。Claude と Google に組み込まれている Gmail コネクタはメールの読み取りと下書き作成はできますが、送信はできず、アシスタントアカウントごとに1つの Google アカウントしか保持できません。送信できるサーバーは通常ローカルプロセスであり、机の上では問題ありませんが、スマホからは見えません。
比較
gmail-mcp | ||||||
実行場所 | Cloudflare Workers | ベンダーがホスト | あなたのサーバーまたはローカル | ローカル | ローカル | ローカル |
スマホからアクセス可能 | ✅ | ✅ | ✅ | ❌ | ❌ | ❌ |
複数のメールボックスを同時に | ✅ 接続ごとに固定 | ❌ | ✅ 呼び出しごとに選択 | ❌ エイリアスのみ | ❌ | ✅ 呼び出しごとに選択 |
メール送信 | ✅ | ❌ | ✅ | ✅ | ✅ | ✅ |
添付ファイル・インライン | ✅ | 未文書化 | ✅ | ✅ | ❌ | ✅ |
引用履歴付き全員返信 | ✅ | ❌ | 下書きのみ | 引用なし | ❌ | ✅ |
転送 | ✅ | ❌ | ✅ | ❌ | ❌ | ✅ |
各パートの文字コードを尊重 | ✅ | — | ❌ UTF-8 前提 | ❌ UTF-8 前提 | ❌ | ❌ |
CRLF ヘッダーインジェクションを拒否 | ✅ | — | ✅ フレームワーク | ✅ 除去 | ❌ なし | ✅ |
メールボックス設定(フィルタ、休暇) | ❌ 対象外 | ❌ | フィルタ | フィルタ | ✅ | ❌ |
ツール数 | 24 | 11–16 | 14 (Gmail) | 30 | 64 | 11 |
リフレッシュトークンの保持者 | あなた | ベンダー | あなた | あなた | あなた | あなた |
google_workspace_mcp は、ここで最も完全なプロジェクトです。Gmail だけでなく Workspace 全体をカバーし、Gmail の署名を追加し、添付ファイルを URL から直接取得しますが、gmail-mcp はどちらも行いません。shinzo-labs/gmail-mcp は、64のツールを通じて休暇応答、委任、S/MIME にアクセスします。これらは gmail.settings.* の下にあり、gmail-mcp が要求しないスコープであるため、権限がどうであれ、その範囲外にあります。
残りの大部分は、2つの設計上の違いで決まります。呼び出し引数でアカウントをルーティングすると、1つの権限ですべての接続済みメールボックスにアクセスできますが、メールボックスを接続に固定すると、誤った引数は何にも到達しません。また、読み取り時にローカルサーバーはすべてのパートを UTF-8 としてデコードします。ISO-2022-JP や Shift_JIS のメールは文字化けし、Gmail が添付ファイルのブロブとして保存する長いメッセージは本文が空で返されます。
Related MCP server: Gmail MCP Connector
デプロイ
約10分です。Cloudflare アカウント、bun、Google アカウントが必要です。Cloudflare アカウントのドメインは任意です — ない場合、Worker は workers.dev で応答します。
1 · Google OAuth クライアントを作成
PROJECT="gmail-mcp-$(openssl rand -hex 3)"
gcloud auth login
gcloud projects create "$PROJECT" --name="gmail-mcp"
gcloud config set project "$PROJECT"
gcloud services enable gmail.googleapis.com次の2つのステップには Google の API がないため、Cloud コンソールで行います。
OAuth 同意画面 → 外部、次に 対象者 の下で アプリを公開 を押します。テスト状態のままにしておくと、Google はすべてのリフレッシュトークンを7日ごとに失効させ、各接続はトークンとともに失われます。公開すると、アプリはサインイン時に未確認アプリの警告を表示し、最大100アカウントに対応します。
認証情報 → 認証情報を作成 → OAuth クライアント ID → ウェブアプリケーション、承認済みのリダイレクト URI として
https://<your-host>/callbackを指定します。クライアント ID とシークレットは保管しておいてください。
<your-host> は Worker に向けるドメイン、または、そうでなければ割り当てられる workers.dev ホスト名です。先にデプロイしてから戻ってきてこれを入力しても問題ありません — Worker が / で提供するガイドに正確な値が表示されます。
2 · Worker をデプロイする
このボタンを押すと、リポジトリが GitHub アカウントにコピーされ、KV 名前空間と Durable Object が作成され、4つのシークレットが要求されます。workers.dev にデプロイされます。カスタムドメインは後で 設定 → ドメインとルート の下で追加します。
代わりにターミナルから:
git clone https://github.com/mkpoli/gmail-mcp && cd gmail-mcp
bun install
bun run setupbun run setup は応答するドメインを尋ね、OAUTH_KV 名前空間を作成または再利用し、クライアント ID とシークレットを受け取り、クッキーキーを生成してデプロイします。最初の2つの回答は wrangler.local.jsonc に保存され、これは git で無視されます — wrangler.jsonc にはどのアカウントの名前空間も誰のドメインも記載されていないため、クローンはどこにでもデプロイできます。単一のシークレットをローテーションするためにセットアップを再実行しても安全です。
3 · クライアントを接続する
クライアント ID とシークレットのフィールドは空のままにしてください — MCP クライアントは自分自身を登録します。
claude mcp add --transport http gmail-personal https://<your-host>/mcp
claude mcp add --transport http gmail-work https://<your-host>/mcp/workClaude Code で /mcp を実行して、各接続をその Google アカウントにサインインさせます。claude.ai では 設定 → コネクタ → カスタムコネクタを追加 で同じ URL を指定します。/mcp/ の後には任意の単一セグメントのラベルを使用でき、これにより、URL を共有する2つのサーバーを拒否するクライアントに対して、1つのデプロイメントで複数のメールボックスを提供できます。
デプロイメントは https://<your-host>/ でこのガイドを提供します。
できること
whoami
search_messages
get_message
get_thread
get_attachment
send_message
reply_all
forward_message
create_draft
update_draft
send_draft
delete_draft
list_drafts
stage_attachment_begin
stage_attachment_append
stage_attachment_finish
list_labels
create_label
update_label
delete_label
modify_labels
modify_thread_labels
batch_modify_messages
trash_message · untrash_message
trash_thread · untrash_thread
メッセージはメールクライアントが送信するのと同じ方法で送信されます: HTML 代替付きのプレーンテキスト、ファイル添付、cid: で参照されるインライン画像が、multipart/mixed › multipart/related › multipart/alternative としてネストされます。件名と表示名は RFC 2047、ファイル名は RFC 2231 を使用するため、日本語、中国語、絵文字もそのまま送信されます。
reply_all は元のメールの Reply-To、From、To、Cc を読み取り、自分のアドレスと送信元として使用するアドレスを除外し、送信者が宛てたアドレスから返信し、References チェーンを引き継ぎ、送信する部分に元のメールを引用します。forward_message は転送されたエンベロープを再現し、元のメールのファイルを再添付できます。
replyToMessageId を指定した create_draft は、送信前に編集する下書きとして返信を作成します: 元のスレッドに参加し、In-Reply-To と References を引き継ぎ、全員返信の受信者と Re: 件名を導出し、元のメールを引用します。update_draft は指定されたフィールドのみを変更します。受信者、テキスト、任意のクライアントで手動で追加されたファイル、下書きが返信するスレッドは読み戻されて保持されます。base64 がツール引数に収まらないファイルは、代わりにステージングされます: stage_attachment_begin は生のバイトを1回の curl -T で受け取るアップロード URL を返し、stage_attachment_append は base64 をチャンクで受け取り、すべての attachments フィールドは結果の stagingId を受け入れます。
読み取りは意図的に制限されています: メッセージとスレッドの本文には文字数の予算があり、応答全体にはバイト数の上限があり、添付ファイルは十分に小さく読める場合にのみインラインで返されます。長いメーリングリストのスレッドや大きなファイルは、アシスタントのコンテキストを埋めるのではなく、その旨の注記付きで切り詰められて返されます。
仕組み
2つの OAuth フローが1つの Worker で合流します。MCP クライアントは Worker に対して認証し、Worker はあなたの代わりに Google に対して認証します。どちらの側も相手の認証情報を保持しません。
sequenceDiagram
autonumber
participant C as MCP client<br/>(Claude Code · claude.ai)
participant W as Worker<br/>(OAuthProvider + McpAgent)
participant G as Google<br/>(OAuth + Gmail API)
C->>W: POST /register (dynamic client registration)
C->>W: GET /authorize (PKCE challenge)
W->>C: approval dialog
C->>G: consent screen — pick the account
G->>W: GET /callback?code=…
W->>W: allowlist check on the verified email
W->>G: exchange code → access + refresh token
W->>C: MCP access token (Google tokens sealed inside the grant)
C->>W: POST /mcp — tools/call
W->>G: Gmail REST (token refreshed as needed)
G->>W: message / thread / label data
W->>C: tool resultレイヤー | ファイル | 役割 |
🔐 MCP 側 OAuth | 動的クライアント登録、PKCE、Google トークンを封印した KV 内のグラント | |
🔗 Google 側 OAuth |
| オフラインアクセス付き認可コード、ブラウザセッションにバインドされたワンタイム state、ダブルサブミット CSRF、検証済みメールの許可リスト |
🤖 エージェント |
| MCP セッションごとに1つの Durable Object、それを開いたアカウントにバインド。シングルフライトのトークン更新、スロットル付きファンアウト |
✉️ メール |
| RFC 822 構築、MIME ツリー走査、文字セットデコード、返信と転送の作成 |
使用技術
TypeScript on Cloudflare Workers — Durable Objects が各 MCP セッションを保持し、KV が OAuth グラントを保持
Hono — OAuth エンドポイント、Google コールバック、
/のセットアップページのルーティング@cloudflare/workers-oauth-provider— MCP クライアントが登録する OAuth 2.1 サーバーagents—McpAgent、Durable Objects 上の MCP トランスポート@modelcontextprotocol/sdkと Zod — ツール定義と引数検証
Gmail 自体は REST API に対する通常の fetch で呼び出されます。公式の googleapis SDK は Node を前提としており、Worker が配布すべき量をはるかに超えるものを含むため、メッセージ構築、MIME 解析、トークン更新は代わりに src/gmail.ts と src/utils.ts にあります。
エンドポイント
パス | 目的 |
| MCP エンドポイント |
| 任意の単一セグメントのラベル下にある同じサーバー。URL を共有する2つのサーバーを拒否するクライアント用 |
| このセットアップガイド |
| OAuth 機構 |
サインインできるユーザー
ALLOWED_EMAILS が、Google が検証済みとして報告するアドレスに対してチェックして決定します — 同意後、グラントが存在する前です。
値 | アクセスできるユーザー |
(空) | 誰もいない |
| それらのアカウント |
| そのドメインの誰でも |
| 検証済みの任意の Google アカウント |
各グラントは認証したメールボックスのみに到達するため、このリストを広げても、すでに接続されているメールボックスへのアクセスが広がることはありません。* を設定すると、見知らぬ人があなたのデプロイメントと Google クライアントの割り当てを自分のメールに使用できるようになります。
制限
共有デプロイメントが枯渇しないようにするための2つの上限があり、どちらも wrangler.jsonc で設定されます:
設定 | 場所 | デフォルト | 制限する内容 |
|
|
| サインインを完了できる異なる Google アカウントのおおよその数。上限に達しても、すでに接続されているアカウントは引き続き機能します。新しいアカウントは拒否されます。同時に到着したサインインは、いずれかが記録される前にそれぞれカウントを読み取るため、合計はこの数より少し上に落ち着くことがあります。Google は未確認アプリを100ユーザーに制限しているため、その下に余裕を残してください。 |
|
|
| そのウィンドウ内で1つのアカウントがすべてのセッションにわたって行える Gmail 呼び出しの数。Cloudflare はこのカウントを場所ごとに保持するため、2つの地域から接続するアカウントはそれぞれでおおよそその数になります。広い読み取りは複数を消費します: 50件を返す |
|
|
| 1つのアドレスがそのウィンドウ内で行えるクライアント登録の数。クライアントは一度登録して付与された ID を保持するため、通常の使用ではこの数に近づくことはありません。この上限があるのは、登録に認証情報が不要で、それぞれが KV に書き込むためです。 |
Workers Free プランではさらに上限が適用されます: 1回の呼び出しにつき50件の送信リクエストです。広範囲の読み取りはメッセージごとに1回消費するため、search_messages と list_drafts はそこで maxResults を45以下にする必要があります。それを超えると、超過分は結果ではなくメッセージごとのエラーとして返されます。有料プランでは1000件まで許可されます。
どちらかを引き上げて再デプロイしてください。Cloudflare のレートリミッターはビルド時にバインディングから上限を読み取るため、各々の simple.limit がそれを変更する唯一の場所です。単一ユーザーのデプロイでは両方ともそのままにしておけます — 通常のアシスタント利用はそれらをはるかに下回ります。
セキュリティ
セルフホスティングは信頼の問題を移すだけで、なくすわけではありません。そこで、すべてがどこにあるのかを以下に示します。
あなたのトークンはあなたのものです。 リフレッシュトークンは、あなたの KV 名前空間内の OAuth グラント内で暗号化されています。セッションの Durable Object は1時間有効なアクセス トークンを保持し、MCP エージェント フレームワークはオブジェクトが存続する間、リフレッシュトークンを含むグラントのコピーをそこに保持します。両方のストアはあなた自身の Cloudflare アカウントであり、保存時に暗号化されています。メールは決して保存されません — 通過するだけです。
1セッション、1メールボックス。 MCP セッションはそれを開いたアカウントにバインドされるため、あるメールボックスのグラントは、借用したセッション ID を通じて別のメールボックスに作用することはできません。
スコープの最小化。
gmail.modifyは読み取り、送信、ラベル、ゴミ箱をカバーします。完全な削除とgmail.settings.*のすべてを除外し、自動転送ルールとフィルターの外部持ち出し — 古典的なメールボックスのバックドア — を、盗まれたグラントでできることの範囲外に置きます。2つの読み取り専用スコープがそれに加えて要求されます:userinfo.emailとuserinfo.profile。これらは許可リストとセッション バインディングがどのアカウントがサインインしたかを知るためのものであり、メールには到達しません。ヘッダーはすり替えられません。 送信されるすべてのヘッダー値は、CR、LF、または NUL を含む場合に拒否されるため、どの引数も自身のフィールドから抜け出して別のフィールドを追加することはできません — たとえば件名行の中の
Bccなど。メディア タイプは検証され、引用された履歴は HTML エスケープされます。これが行わないのは、引数自体を取り締まることです:bccは実際のパラメータであるため、メッセージ本文に隠された指示に基づいて行動するモデルがそれを埋める可能性は依然としてあり、クライアントの承認プロンプトがそのチェックとして残ります。アクセスは取り消せます。
ALLOWED_EMAILSを狭めると、新しいサインインが停止します。単一アカウントのアクセスは myaccount.google.com/connections で取り消されます。Google クライアント シークレットをローテーションすると、すべてのグラントが一度に無効になります。
Worker はリクエストの処理中にメールをメモリ内で復号化します。これは、ホスト型リレーが必ず行うことです。特定のメールボックスにとってそれが受け入れられない場合は、そのメールボックス用にローカル MCP サーバーを実行してください。
テスト方法
253のユニット テストが、メッセージ構築 (MIME ネスト、RFC 2047 折り返し、RFC 2231 ファイル名、CR/LF 拒否、base64 ラッピング)、文字セットをまたぐ本文抽出、返信と転送の作成、Google トークン フロー、サインイン許可リスト、サインインのブラウザ側を保護する CSRF と状態バインディングのチェック、そして Gmail の代役に対するツール自体 — セッション所有権、受信者構成、添付ファイル選択、部分的に失敗した読み取りが返すもの — をカバーしています。
それに加えて、すべてのツールが実際の Gmail アカウントに対して実行され、別のアカウントが届いたものを確認しました:
領域 | 結果 |
エンコーディング | 日本語の件名がエンコードされた単語に折り返されました。絵文字、ZWJ シーケンス、RTL アラビア語、結合記号、および稀な CJK がバイト単位で同一のまま往復しました |
添付ファイル |
|
スレッド化 |
|
2つのアカウント | 両方が同時に1つのデプロイに接続されました。一方からのメッセージ ID は他方で |
整理 | ネストされた CJK ラベルが作成、名前変更、一括適用、削除されました。スレッドとメッセージのゴミ箱が両方とも元に戻されました |
スケール | 15,000メッセージのメールボックスが Gmail 演算子とページネーションで検索され、レート制限に抵触しませんでした |
開発
bun run dev # wrangler dev on :8788
bun run check # biome + tsc
bun test # 253 unit tests
bun run assets # regenerate the light and dark diagrams
bun run deploy質問とバグ
issue を開いてください。
ライセンス
Copyright © 2026 mkpoli。MIT License の下で公開されています。
src/workers-oauth-utils.ts は cloudflare/ai 内の remote-mcp-github-oauth デモ から派生したもので、Copyright © 2025 Cloudflare, Inc.、MIT License の下で使用されています。THIRD-PARTY.md を参照してください。
This server cannot be installed
Resources
Unclaimed servers have limited discoverability.
Looking for Admin?
If you are the server author, to access and configure the admin panel.
Related MCP Servers
- AlicenseNot gradedqualityDmaintenanceEnables interaction with Gmail through the MCP protocol, supporting sending, reading, searching, replying, forwarding, managing drafts and labels, and saving attachments.123MIT
- AlicenseNot gradedqualityBmaintenanceA Gmail MCP server running on Cloudflare Workers that enables reading, searching, labeling, drafting, sending, and managing Gmail messages, including fetching raw attachment bytes, with per-user OAuth authorization.231MIT
- AlicenseNot gradedqualityCmaintenancegmail-mcp is a remote MCP server that exposes Gmail as a set of tools — search, read, label, draft, send — over streamable HTTP with OAuth 2.1. It runs on Cloudflare Workers under your own domain.2317MIT
- AlicenseNot gradedqualityCmaintenanceA Gmail MCP server that lets AI assistants search, read, send, and manage email across multiple Google accounts, deployed on Cloudflare Workers.231MIT
Related MCP Connectors
Read, search, send, organize, draft and schedule email across your inboxes from any MCP client.
Manage Gmail end-to-end: search, read, send, draft, label, and organize threads. Automate workflow…
Manage Gmail messages, threads, labels, drafts, and settings from your workflows. Send and organiz…
Latest Blog Posts
- Who's Calling? MCP Hosts Are an Identity Blind Spot (And the Spec Knows It)By Om-Shree-0709 on .mcpAgent IdentityOAuth 2.1
- Your AI Chatbot Just Exposed Your CEO's Salary to an InternBy Om-Shree-0709 on .Agent IdentityMCP SecurityOAuth Delegation
- Why MCP Servers Need Execution Sandboxing (And Why Your Current Stack Isn't Enough)By Om-Shree-0709 on .Agentic AiPrompt InjectionWebAssembly
MCP directory API
We provide all the information about MCP servers via our MCP API.
curl -X GET 'https://glama.ai/api/mcp/v1/servers/Skraelingen/gmail-mcp-kevin'
If you have feedback or need assistance with the MCP directory API, please join our Discord server