mcpField
O
oauth-auditor

oauth-auditor

ローカル
github.com/GuardBeeセキュリティ11 日前に更新

oauth-auditor について

oauth-auditorは、MCPサーバーのOAuth認可コードを監査する開発者向けMCPサーバーです。指定されたOAuth 2.1のアンチパターンを検出し、CI/CD向けにSARIFを出力できます。

主な機能

  1. 016種類のOAuthアンチパターンを検出
  2. 02ソースファイルとディレクトリを検査
  3. 03SARIF 2.1.0形式で出力
  4. 04guardbee.ymlによる設定

活用シーン

  1. 01リリース前のMCPサーバー認可コードの確認
  2. 02CI/CDへのOAuthチェックの追加
  3. 03コード断片やファイルの認可リスク検査

MCP 対応

テキスト、ファイル、ディレクトリのスキャンと、対応パターンの一覧表示を行うMCPツールを提供します。コードスキャンと稼働中エンドポイントのプローブにはコマンドラインも利用できます。

設定

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

mcp.json · 共通設定
{
"mcpServers": {
"4hmetuyar-oauth-auditor": {
"command": "npx",
"args": [
"-y",
"@guardbee/mcp-oauth-auditor"
]
}
}
}
起動コマンドnpx -y @guardbee/mcp-oauth-auditor

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

パッケージ
npm@guardbee/mcp-oauth-auditor0.1.2

ツール

4

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

パラメーター型必須説明
labelstringいいえ検出結果に表示する任意のラベル(例:ファイル名)
contentstringはいスキャンするコードの内容

詳細

@guardbee/mcp-oauth-auditor

🇬🇧 English | 🇹🇷 Türkçe | 🇨🇳 中文 | 🇯🇵 日本語 | 🇰🇷 한국어 | 🇧🇷 Português | 🇪🇸 Español | 🇩🇪 Deutsch

npm version npm downloads License: MIT

MCP(Model Context Protocol)サーバー自身の認可コードをスキャンし、MCP 仕様の「セキュリティに関する考慮事項」セクションで明示されているOAuth 2.1 のアンチパターンを検出する MCP サーバーです。

MCP 仕様はこれを曖昧なままにしていません。OAuth リソースサーバーとして動作するサーバーにおける認可の主な失敗パターンとして、トークンパススルー(クライアントのトークンを交換やスコープの再設定をせず、そのまま下流 API に転送すること)と、オーディエンス検証の欠如(aud クレームがこのサーバー向けに発行されていないトークンを受け入れること)を明確に挙げています。このパッケージは、まさにこの 2 つに加え、同じカテゴリーに属する関連アンチパターンを 3 つ検査します。

テレメトリーはデフォルトでオフです。GUARDBEE_TELEMETRY=1 を設定すると、サーバー、ツール、成功状態、処理時間、ファイルパスなどの短いパラメーター値が送信されます。長い文字列や content、token、password などのフィールドはプレースホルダーに置き換えられます。詳細は @guardbee/mcp-telemetry をご覧ください。

Claude ──► oauth-auditor ──► Your MCP server's auth code
              │
              ├─ token-passthrough    (client's token forwarded unchanged downstream)
              ├─ token-validation     (jwt.verify() with no audience check)
              ├─ discovery-ssrf       (OAuth/OIDC discovery URL built from client input)
              ├─ pkce                 (authorization request missing code_challenge)
              ├─ redirect-validation  (redirect_uri checked with startsWith/includes, not exact match)
              └─ secrets-exposure     (hardcoded client_secret)

この 2 つを特に取り上げる理由

トークンパススルーが問題となるのは、クライアントがこのサーバーに提示したトークンは、このサーバー向けにスコープとオーディエンスが設定されており、サーバー自身のツールハンドラーが次に呼び出す下流 API 向けではないためです。トークンをそのまま転送すると、下流サービスは自らが発行したのではない認証情報を信頼することになります。その根拠となるのは、元のトークン発行者が承認していないサーバー側の判断です。

オーディエンス検証の欠如は、逆方向から見た同じ失敗です。jwt.verify(token, key) はトークンの署名が有効であることを確認しますが、誰に向けて発行されたのかは何も示しません。明示的な audience チェックがなければ、まったく無関係なリソースサーバー向けに発行されたトークンでも、同じ発行者や署名鍵を共有しているというだけで、ここでも検証に成功します。これは、MCP 仕様が警告している典型的な「混乱した代理人」へのすり替えです。

残る 3 つのパターンも、「MCP サーバーの認証コードが信頼すべきでないものを信頼している」という同じテーマに隣接する具体例です。実際に公表された CVE の原因となった形式で、クライアントが指定した入力から OAuth/OIDC のディスカバリー URL を構築すること、完全一致ではなくプレフィックスや部分文字列で redirect_uri を検証すること(オープンリダイレクトの回避)、そして認可リクエストで PKCE が暗黙のうちに欠落することです(OAuth 2.1 ではパブリッククライアントに限らず、無条件に必須です)。


機能

  • 6 categories:token-passthrough、token-validation、discovery-ssrf、pkce、redirect-validation、secrets-exposure
  • 2 つのチェック(audience 検証の欠如、PKCE の欠如)は、固定の正規表現ではなく、呼び出し箇所付近に存在しないことを調べます。jwt.verify(...) の呼び出し全体(または認可リクエスト URL の構築)を抽出し、audience: / code_challenge が付近に本当に存在しないことを確認します。たまたま文字列の位置が一致しただけの場合は検出しません。
  • SARIF 2.1.0 出力 — CI/CD との統合(GitHub Code Scanning など)
  • guardbee.yml による設定ファイルのサポート
  • 18 件の単体テスト — 各パターンに肯定シナリオと否定(誤検出)シナリオを用意し、検出結果がゼロになる完全に正しい OAuth フローを 1 件用意しています。開発中に実際の正規表現のバグを発見して修正しました(] の後にある末尾の \b は、] が単語文字ではないため一致しません。これにより、ヘッダーアクセスのブラケット記法がひそかに見逃されていました)。6 つすべてのアンチパターンを意図的に仕込んだフィクスチャでエンドツーエンド検証を実施し、6 件すべてを検出しました。また、guardbee-mcp モノレポ全体(401 ファイル)に対しても検証し、実際のサードパーティコードでは検出結果がゼロでした。テスト以外で一致したのはスキャナー自身のパターン定義で、正規表現リテラル内の文字列 jwt.verify( とドキュメントコメントに含まれる文字列だけであり、実際の脆弱な使用ではありませんでした。

クイックスタート

Claude Desktop / MCP クライアント
{
  "mcpServers": {
    "guardbee-oauth-auditor": {
      "command": "npx",
      "args": ["-y", "@guardbee/mcp-oauth-auditor"]
    }
  }
}
CLI(CI/CD)
npx @guardbee/mcp-oauth-auditor scan ./src --fail-on=high --format=sarif > results.sarif

MCP ツール

ツール説明
scan_textコードスニペットをスキャンします
scan_file単一のファイルをスキャンします
scan_directoryディレクトリを再帰的にスキャンします
list_patternsカテゴリー別に、サポートされているすべてのパターンを一覧表示します

検出されるパターン

カテゴリーパターン深刻度OWASP
token-passthroughtoken_passthrough_to_downstreamcriticalMCP07
token-validationmissing_audience_validationhighMCP07
discovery-ssrfoauth_discovery_ssrfcriticalMCP07
pkcemissing_pkce_on_auth_requesthighMCP07
redirect-validationloose_redirect_uri_validationhighMCP07
secrets-exposurehardcoded_oauth_client_secrethighMCP07
state-handlepredictable_state_handle(+ Python) — Math.random、Date.now、カウンターから生成された state / セッションハンドルhighMCP07
state-handlestate_handle_not_bound_to_user — ツール引数から取得したハンドルを検索する際、呼び出し元本人のものかどうかを確認していないmediumMCP07
mix-upmissing_iss_validation — iss を検証せずに認可コードを交換している(RFC 9207)mediumMCP07
auth-urlauth_url_scheme_not_validated — サーバーから提供された URL をスキームの検証なしで開いている(javascript:、data:、file:)highMCP07
auth-urlauth_url_opened_via_shell — URL をシェル経由で open / xdg-open / start に渡しているcriticalMCP05
local-exposurelocal_http_server_unauthenticated — 認証のない HTTP MCP トランスポートhighMCP07
local-exposuremissing_host_origin_check — Host / Origin の検証がない(DNS リバインディング)mediumMCP07
local-exposurelisten_all_interfaces — MCP サーバーが 0.0.0.0 にバインドされているmediumMCP07
Python と Go

言語はファイル拡張子から判定され、Python 固有および Go 固有のルールは、それぞれの言語のファイルに対してのみ実行されます。

  • Python(FastAPI / Starlette / Flask、PyJWT、python-jose、authlib):python_missing_audience_validation(audience= を指定せず、authlib の claims_options に aud もない jwt.decode)、python_audience_verification_disabled("verify_aud": False)、python_token_passthrough_to_downstream(requests / httpx / クライアント呼び出しでの Authorization ヘッダーまたは request.headers 全体の転送)、code_challenge を指定せずに authlib の create_authorization_url / authorize_redirect を使う場合の missing_pkce_on_auth_request、およびディスカバリーの SSRF、リダイレクト、state、0.0.0.0 に関するルール。
  • Go(golang-jwt / jwx、go-oidc、golang.org/x/oauth2、go-sdk、mcp-go の HTTP トランスポート):go_missing_audience_validation(jwt.WithAudience を指定しない jwt.Parse)、go_oidc_client_id_check_skipped、go_token_passthrough_to_downstream(out.Header.Set("Authorization", r.Header.Get("Authorization")))、go_hardcoded_oauth_client_secret、go_loose_redirect_uri_validation(strings.HasPrefix)、go_predictable_state_handle(math/rand、time)、go_oauth_discovery_ssrf、go_auth_url_opened_via_shell、S256ChallengeOption を指定せずに AuthCodeURL を使う場合の missing_pkce_on_auth_request、および ListenAndServe(":8080") を listen_all_interfaces として検出するルール。
  • 両方:token_passthrough_via_variable — 受信した Authorization ヘッダーを変数に読み込み、その変数を送信リクエストに設定するケース。

各検出結果は、該当する MCP spec Security Best Practices のセクションにリンクし(SARIF の helpUri)、SARIF タグとして OWASP MCP Top 10 の ID を付与します。新しいルールは、1 ファイルずつを対象にしたヒューリスティックです。別のモジュールで実施されるチェック(認証ミドルウェアや、ヘルパー内の iss 比較など)は検出されません。

ライブプローブ
npx @guardbee/mcp-oauth-auditor probe http://127.0.0.1:3000/mcp

実行中の HTTP MCP エンドポイントに対する読み取り専用チェックです。認証情報なしで initialize に応答するか(probe_unauthenticated_access)、外部の Host(probe_dns_rebinding_host_accepted)または Origin(probe_foreign_origin_accepted)を受け入れるかを確認します。認証情報は送信せず、initialize 以外は呼び出さず、開いたセッションはすべて閉じます。また、--allow-public が指定されていない限り、パブリックアドレスに解決されるホストは拒否します。CLI 専用です。エージェントは MCP ツールを通じて起動できません。


設定(guardbee.yml)

oauth-auditor:
  fail-on: high       # any | critical | high | medium | none
  max-files: 5000
  exclude:
    - ".test.ts"

制限事項(設計上のもの)

  • TypeScript/JavaScript、Python、Go。 それぞれ、一般的なライブラリ向けのルールがあります(上記参照)。その他の言語(Rust、Java、C#、…)やライブラリは、リテラルの client_secret や response_type=code など、これらと同じ形式に当てはまる場合にのみ検出されます。
  • 完全な OAuth 適合性テストではなく、ヒューリスティックです。 実行中の認可サーバーに対するライブプロトコル適合性チェックではなく、ソースコード内の特定のアンチパターンを検出します。OAuth フローのあらゆる誤実装を検出するわけではなく、MCP 仕様が最も重大なものとして挙げている一部のみを対象とします。
  • audience と PKCE の有無に基づくチェックでは、範囲を限定したテキストウィンドウを使用し、実際のパーサーは使いません。 呼び出し箇所から遠く離れた場所でオプションオブジェクトが構築されている jwt.verify() 呼び出し(インラインオブジェクトではなく、変数が渡されるケース)では、audience が正しくチェックされない場合があります。

開発

npm run build
npm test

ライセンス

MIT — GuardBee

フィードバック

質問、アイデア、誤検出などがあれば、GitHub Discussions でスレッドを立てるか、issue を作成してください。GuardBee が役に立った場合は、リポジトリに ⭐ を付けていただけると、ほかの人にも見つけてもらいやすくなります。

コメント

MCP は初めてですか?

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

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