MCP 規範完整中譯稿:2025-3-26 版

【引】儘管 AI 可以幫助我們順利地理解 MCP 規範,但一份完整的 MCP 規範中譯稿還是有意義的,可以進一步幫助我們理解 MCP 規範的來龍去脈,以及協議中細節的方方面面。如果希望希望極簡入門的話, 可以閱讀老碼農的新作——

1. 規範

模型上下文協議 (Model Context Protocol,MCP) 是一個開放的協議,支持 LLM 應用程序與外部數據源和工具之間的無縫集成。無論是構建基於 AI 的 IDE、增強聊天界面還是創建自定義 AI 工作流,MCP 都提供了一種標準化的方法來將 llm 與它們所需的上下文連接起來。

該規範基於 schema.ts 中的 TypeScript 模式定義了權威協議需求。

有關實現指南及示例,請瀏覽 modelcontextprotocol.io。

本文件中的關鍵詞 “MUST”、“MUST NOT”、“REQUIRED”、“SHALL”、“SHALL NOT”、“SHOULD”、“SHOULD NOT”、“RECOMMENDED”、“NOT RECOMMENDED”、“MAY” 和 “OPTIONAL” 應按照 BCP 14 [RFC2119][RFC8174] 中的規定解釋,如本文件所示,當且僅當它們出現在所有大寫字母中時表示如上含義。

1.1 概覽

MCP 爲應用程序提供了一種標準化的方式:

該協議使用 JSON-RPC 2.0 消息來建立以下組件之間的通信:

MCP 從語言服務器協議 (Language Server Protocol) 中獲得了一些靈感,該協議標準化瞭如何在整個開發工具生態系統中添加對編程語言的支持。以類似的方式,MCP 標準化瞭如何將其他上下文和工具集成到 AI 應用程序的生態系統中。

1.2 主要內容

1.2.1 基本協議

1.2.2 特性

服務器向客戶端提供以下特性:

客戶端可向服務器提供以下功能:

1.3 安全性和信任及保護

模型上下文協議通過任意的數據訪問和代碼執行路徑實現了強大的功能。這種能力帶來了重大的安全和信任問題,所有實現者都必須仔細考慮這些問題。

1.3.1 主要原則

1. 用戶同意及管制

實現者應該爲審查和授權活動提供清晰的用戶界面

2. 數據私隱

3. 工具安全

4. 採樣控制

雖然 MCP 本身不能在協議級別上強制執行這些安全原則,但實現者應該:

2. 關鍵變更

本文檔列出了自上一版本( 2024-11-05 )以來對模型上下文協議 (MCP) 規範所做的變更。

2.1 主要變化

2.2  其他模式的變更

有關更多詳細信息,請參見更新的數據模式。

2.3 完整的變更記錄

有關自上次協議修訂以來所做的所有變更的完整列表,請參見 GitHub。

3. 架構

模型上下文協議 (Model Context Protocol,MCP) 遵循客戶端 - 主機 - 服務器的架構模式,其中每個主機可以運行多個客戶端實例。這種架構使用戶能夠在應用程序之間集成 AI 功能,同時保持清晰的安全邊界和隔離關注點。MCP 建立在 JSON-RPC 之上,它提供了一個有狀態的會話協議,主要關注客戶端和服務器之間的上下文交換和採樣協調。

3.1 核心組件

3.1.1 主機(Host)

主機進程充當容器和協調器:

3.1.2 客戶端(client)

每個客戶端由主機創建,並維護一個獨立的服務器連接:

主機應用程序創建並管理多個客戶機,每個客戶機與特定服務器具有 1:1 的關係。

3.1.3 服務器(Server)

服務器提供專門的環境和功能:

3.2 設計原則

MCP 建立在幾個關鍵設計原則的基礎上,這些原則爲其架構和實施提供了參考信息:

3.2.1 服務器應該非常容易構建

3.2.2 服務器應該是高度可組合的

3.2.3 服務器不能夠讀取整個會話,也不能 “看到” 其他服務器

3.2.4 功能特性可以逐步添加到服務器和客戶端

3.3 能力協商

模型上下文協議使用一個基於能力的協商系統,客戶端和服務器在初始化期間顯式地聲明它們支持的功能特性。能力決定哪些協議特性和原語在會話期間可用。

每個功能解鎖特定的協議特性,以便在會話期間使用。例如:

此能力協商確保客戶端和服務器在維護協議可擴展性的同時清楚地理解所支持的功能。

4. 基本協議

修訂於 2025 年 3 月 26 日

4.1 概覽

模型上下文協議由幾個協同工作的關鍵組成部分組成:

所有的實現都必須支持基本協議和生命週期管理組件。其他組件可以根據應用程序的具體需要來實現。

這些協議層建立了清晰的關注點分離,同時實現了客戶端和服務器之間的豐富交互。模塊化設計允許實現完全支持它們需要的特性。

4.1.1 消息

MCP 客戶端和服務器之間的所有消息必須遵循 JSON-RPC 2.0 規範,該協議定義了以下類型的消息。

4.1.1.1 請求

請求從客戶端發送到服務器,反之亦然,以啓動一個操作。

{
  jsonrpc: "2.0";
  id: string | number;
  method: string;
  params?: {
    [key: string]: unknown;
  };
}

4.1.1.2 響應

響應是在回覆請求時發送的,包含操作的結果或錯誤信息。

{
  jsonrpc: "2.0";
  id: string | number;
  result?: {
    [key: string]: unknown;
  }
  error?: {
    code: number;
    message: string;
    data?: unknown;
  }
}

通知作爲單向消息從客戶機發送到服務器,反之亦然。接收者不能發送響應。

{
  jsonrpc: "2.0";
  method: string;
  params?: {
    [key: string]: unknown;
  };
}

通知不能包含 ID。

4.1.1.3 批處理

JSON-RPC 還定義了一種方法來批處理多個請求和通知,將它們發送到一個數組中。MCP 實現可能支持發送端的 JSON-RPC 批處理,但必須支持接收端的 JSON-RPC 批處理。

4.1.2 授權

MCP 提供了一個用於 HTTP 的授權框架。使用基於 http 傳輸的實現應該符合這個規範,而使用 STDIO 傳輸的實現不應該遵循這個規範,而應該從環境中檢索憑證。

此外,客戶端和服務器可以協商自己的自定義身份驗證和授權策略。

欲瞭解更多關於 MCP 身份驗證機制發展的討論和貢獻,請加入 GitHub 討論,幫助塑造協議的未來!

4.1.3 Schema

協議的完整規範被定義爲 TypeScript 模式。這是所有協議消息和結構的真實來源。

還有一個 JSON Schema,它是從 TypeScript 可信真值源自動生成的,用於各種自動化工具。

4.2 生命週期

模型上下文協議 (Model Context Protocol,MCP) 爲客戶端 - 服務器連接定義了嚴格的生命週期,以確保適當的能力協商和狀態管理。

  1. 初始化: 能力協商和協議版本認同

  2. 操作: 正常協議通信

  3. Shutdown: 連接的正常終止

4.2.1 生命週期階段

4.2.1.1 初始化

初始化階段必須是客戶端和服務器之間的第一次交互。在這個階段,客戶端和服務器:

客戶端必須通過發送包含以下內容的初始化請求來啓動此階段:

{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "initialize",
  "params": {
    "protocolVersion": "2024-11-05",
    "capabilities": {
      "roots": {
        "listChanged": true
      },
      "sampling": {}
    },
    "clientInfo": {
      "name": "ExampleClient",
      "version": "1.0.0"
    }
  }
}

初始化請求不能成爲 JSON-RPC 批處理的一部分,因爲在初始化完成之前,其他請求和通知是不可能發出的。這還允許向後兼容不顯式支持 JSON-RPC 批處理的以前協議版本。

服務器必須用自己的能力和信息進行響應:

{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "protocolVersion": "2024-11-05",
    "capabilities": {
      "logging": {},
      "prompts": {
        "listChanged": true
      },
      "resources": {
        "subscribe": true,
        "listChanged": true
      },
      "tools": {
        "listChanged": true
      }
    },
    "serverInfo": {
      "name": "ExampleServer",
      "version": "1.0.0"
    },
    "instructions": "Optional instructions for the client"
  }
}

初始化成功後,客戶端必須發送一個初始化通知,表明它已準備好開始正常操作:

{
  "jsonrpc": "2.0",
  "method": "notifications/initialized"
}

4.2.1.2 版本協商

在初始化請求中,客戶端必須發送它支持的協議版本。這應該是客戶端支持的最新版本。

如果服務器支持請求的協議版本,它必須用相同的版本響應。否則,服務器必須使用其支持的另一個協議版本進行響應。這應該是服務器支持的最新版本。

如果客戶端不支持服務器響應中的版本,它應該斷開連接。

4.2.1.3 能力協商

客戶端和服務器功能確定在會話期間哪些可選協議的特性可用。

主要能力包括:

aKNiSs

能力對象可以像這樣描述其子能力:

4.2.1.4 操作

在操作階段,客戶端和服務器根據協商的能力交換消息。

雙方應該:

4.2.1.5 shutdown

在關閉階段,一方 (通常是客戶端) 乾淨地終止協議連接。沒有定義特定的關閉消息ーー相反,應該使用底層傳輸機制來發送連接終止信號:

stdio

對於 stdio 傳輸,客戶端應該通過以下方式啓動關閉:

  1. 首先,關閉子進程 (服務器) 的輸入流

  2. 等待服務器退出,如果服務器沒有在合理的時間內退出,則發送 SIGTERM

  3. 如果服務器沒有在 SIGTERM 之後的合理時間內退出,則發送 SIGKILL

服務器可以通過關閉其到客戶端的輸出流並退出來啓動關閉。

HTTP

對於 HTTP 傳輸,通過關閉相關的 HTTP 連接來指示關閉。

4.2.1.6 超時

實現應該爲所有發送的請求建立超時,以防止掛起連接和資源耗盡。當請求在超時期間內沒有收到成功或錯誤響應時,發送方應該爲該請求發出取消通知,並停止等待響應。

SDK 和其他中間件應該允許根據每個請求配置這些超時。

實現可能在接收到相應請求的進度通知時選擇重置超時時鐘,這意味着工作實際上正在發生。但是,無論進度通知如何,實現都應該強制執行最大超時,以限制行爲不當的客戶端或服務器的影響。

4.2.1.7 錯誤處理

應該準備好實現來處理這些錯誤情況:

{
  "jsonrpc": "2.0",
  "id": 1,
  "error": {
    "code": -32602,
    "message": "Unsupported protocol version",
    "data": {
      "supported": ["2024-11-05"],
      "requested": "1.0.0"
    }
  }
}

4.3 傳輸

MCP 使用 JSON-RPC 編碼消息。 JSON-RPC 消息必須是 utf-8 編碼。

該協議目前定義了客戶端 - 服務器通信的兩種標準傳輸機制:

客戶端應該儘可能支持 stdio。

客戶端和服務器也可以以可插拔的方式實現自定義傳輸。

4.3.1 STDIO

在 STDIO 的傳輸中:

4.3.2 Streamable HTTP

這取代了協議 2024-11-05 版本中的 HTTP + SSE 傳輸。

在 Streamable HTTP 傳輸中,服務器作爲獨立進程運行,可以處理多個客戶端連接。此傳輸使用 HTTP POST 和 GET 請求。服務器可以選擇性地使用 SSE 來流化多個服務器消息。這爲基本的 MCP 服務器和支持流的服務器提供了更多豐富的功能,並支持服務器到客戶端的通知和請求。

服務器必須提供一個同時支持 POST 和 GET 方法的 HTTP 端點路徑 (以下稱爲 MCP 端點)。例如,這可能是一個類似於 https://example.com/mcp 的 URL。

4.3.2.1 安全警告

實現流式 HTTP 傳輸時:

  1. 服務器必須在所有傳入連接上驗證初始的 HTTP 頭,以防止 DNS 重新綁定攻擊

  2. 在本地運行時,服務器應該只綁定到本地主機 (127.0.0.1) ,而不是綁定到網絡接口 (0.0.0.0) 

  3. 服務器應該爲所有連接實現正確的身份驗證

如果沒有這些保護,攻擊者可以使用 DNS 重新綁定來與遠程站點的本地 MCP 服務器交互。

4.3.2.2 向服務器發送消息

從客戶端發送的每個 JSON-RPC 消息都必須是對 MCP 端點的新 HTTP POST 請求。

  1. 客戶端必須使用 HTTP POST 將 JSON-RPC 消息發送到 MCP 端點。

  2. 客戶機必須包含一個 Accept 頭,列出將 application/json 和 text/event-stream 作爲支持的內容類型。

  3. POST 請求的正文 MUST 必須列情況之一:

    • 單個 JSON-RPC 請求、通知或響應

    • 批處理一個或多個請求和 / 或通知的數組

    • 批處理一個或多個響應的數組

  4. 如果輸入僅由 (任意數量的) JSON-RPC 組成響應或者通知:

    • 如果服務器接受輸入,則服務器必須返回 HTTP 狀態碼 202 Accepted,而不接受任何正文。

    • 如果服務器不能接受輸入,它必須返回一個 HTTP 錯誤狀態碼 (例如,400 Bad Request)。HTTP 響應的正文可能包含一個沒有 id 的 JSON-RPC 錯誤響應。

  5. 如果輸入包含任意數量的 JSON-RPC 請求,服務器必須返回 Content-Type: text/event-stream 來初始化 SSE 流,或者返回 Content-Type: application/JSON 來返回一個 JSON 對象。客戶端必須同時支持這兩種情況。

  6. 如果服務器啓動 SSE 流:

    • 斷開連接不應被解釋爲客戶端取消其請求。

    • 若要取消其請求,客戶端應顯式發送 MCP CancelledNotification。

    • 爲了避免由於斷開連接而導致的消息丟失,服務器可以恢復流傳輸。

    • SSE 流最終應該爲 POST 主體中發送的每個 JSON-RPC 請求包含一個 JSON-RPC 響應。這些響應可以是批處理形式。

    • 在發送 JSON-RPC 響應之前,服務器可能會發送 JSON-RPC 請求和通知。這些消息應該與原始客戶端的請求相關。這些請求和通知可以被批處理。

    • 服務器不應該在爲每個接收到的 JSON-RPC 請求發送一個 JSON-RPC 響應之前關閉 SSE 流,除非會話過期。

    • 在發送了所有 JSON-RPC 響應之後,服務器應該關閉 SSE 流。 斷開連接可以發生在任何時間 (例如,由於網絡條件),因此:

4.3.2.3 偵聽來自服務器的消息

  1. 客戶端可以向 MCP 端點發出 HTTP GET 請求。這可以用來打開一個 SSE 流,允許服務器與客戶端通信,而不需要客戶機首先通過 HTTP POST 發送數據。

  2. 客戶端必須包含一個 Accept 頭,將 text/event-stream 列爲受支持的內容類型。

  3. 服務器必須返回 Content-Type: text/event-stream 來響應這個 HTTP GET,或者返回 HTTP 405 Method Not Allowed,表明服務器沒有在這個端點提供 SSE 流。

  4. 如果服務器啓動了 SSE 流:

    • 服務器可以在流上發送 JSON-RPC 請求和通知。這些請求和通知可以被批處理。

    • 這些消息應該與來自客戶端的任何併發運行的 JSON-RPC 請求無關。

    • 服務器不能在流上發送 JSON-RPC 響應,除非恢復與以前的客戶端請求相關聯的流。

    • 服務器可以在任何時候關閉 SSE 流。

    • 客戶端可以在任何時候關閉 SSE 流。

4.3.2.4 多連接

  1. 客戶端可以同時保持與多個 SSE 流的連接。

  2. 服務器必須只在一個已連接的流上發送它的每個 JSON-RPC 消息;也就是說,它絕對不能跨多個流廣播相同的消息。

    • 可以通過使流可恢復來降低消息丟失的風險。

4.3.2.5 可恢復性和重新發送

爲了支持恢復中斷的連接,並重新發送可能丟失的消息:

  1. 服務器可以附上一個 id 字段並添加到它們的 SSE 事件,像 SSE 標準描述的那樣:

    • 如果存在該 ID ,則必須在該會話內的所有流之間是全局唯一的ーー或者在不使用會話管理的情況下在具有該特定客戶端的所有流之間是全局唯一的。
  2. 如果客戶端希望在斷開連接後恢復,則它應該向 MCP 端點發出一個 HTTP GET 請求, 並將使用 Last-Event-ID 頭來指示它接收的最後一個事件 ID。

    • 服務器可以使用這個頭來重播在最後一個事件 ID 之後發送的消息,並在斷開連接的流上從該點恢復流。

    • 服務器一定不能重播在不同流上傳遞的消息。

換句話說,服務器應該根據每個流分配這些事件 id,作爲該特定流中的遊標。

4.3.2.6 會話管理

一個 MCP “會話” 由客戶端和服務器之間邏輯上相關的交互組成,從初始化階段開始。未來支持希望建立有狀態會話的服務器:

  1. 使用流式 HTTP 傳輸的服務器可以在初始化時分配會話 ID,方法是將其 HTTP 響應頭 Mcp-Session-Id header 中包含 InitializeResult.

    • 會話 ID 應該是全局唯一的,並且具有加密安全性 (例如,安全生成的 UUID、 JWT 或加密散列)。

    • 會話 ID 必須只包含可見的 ASCII 字符 (範圍從 0x21 到 0x7e)。

  2. 如果服務器在初始化期間返回 Mcp-Session-Id ,客戶端使用流式 HTTP 傳輸時必須在所有後續 HTTP 請求頭中包含 Mcp-Session-Id 。

    • 需要會話 ID 的服務器應該使用 HTTP 400 Bad Request 來響應沒有 Mcp-Session-Id 頭的請求 (初始化除外)。
  3. 服務器可以在任何時候終止會話,之後它必須用 HTTP 404 Not Found 響應包含該會話 ID 的請求。

  4. 當客戶端響應包含 Mcp-Session-Id 的請求而收到 HTTP 404 時,它必須通過發送一個沒有附加會話 ID 的新 InitializeRequest 來啓動一個新會話。

  5. 不再需要特定會話的客戶端 (例如,因爲用戶即將離開客戶端應用) 應該發送 HTTP DELETE 到 MCP 端點,並使用 Mcp-Session-Id 頭以顯式終止會話。

    • 服務器可能用 HTTP 405 Method Not Allowed 響應此請求,表示服務器不允許客戶端終止會話。  

4.3.2.7 向後兼容性

客戶端和服務器可以維護與 HTTP+ SSE 傳輸 (來自協議版本 2024-11-05) 的向後兼容性,如下所示:

希望支持老客戶端的服務器應該:

希望支持舊服務器的客戶端應該:

  1. 接受來自用戶的 MCP 服務器 URL,該 URL 可以指向使用舊傳輸協議或新傳輸協議的服務器。

  2. 試圖 POST 一個 InitializeRequest 到服務器 URL,使用如上所述的 Accept 頭:

4.3.2.8 定製傳輸

客戶短和服務器可以實現額外的自定義傳輸機制,以滿足它們的特定需求。該協議是傳輸無關的,可以在任何支持雙向消息交換的信道上完成實現。

選擇支持自定義傳輸的實現者必須確保它們保留由 MCP 定義的 JSON-RPC 消息格式和生命週期需求。自定義傳輸應該記錄其特定的連接建立和消息交換模式,以幫助實現互操作性。

4.4 鑑權

4.4.1. 簡介

4.4.1.1 目標及範圍

模型上下文協議在傳輸級別提供鑑權功能,使 MCP 客戶短能夠代表資源所有者向受限 MCP 服務器發出請求。本規範定義了基於 HTTP 傳輸的授權流程。

4.4.1.2 協議要求

對於 MCP 實現,鑑權是可選的。當支持鑑權時:

4.4.1.3 遵守標準

這種鑑權機制基於下列既定規範,但實現了其特性的一個選定子集,以確保安全性和互操作性,同時保持簡單:

4.4.2. 鑑權流程

4.4.2.1 概覽

  1. MCP 鑑權實現必須實現 OAuth 2.1,併爲私密客戶端和公共客戶端提供適當的安全措施。

  2. MCP auth 實現應該支持 OAuth 2.0 動態客戶端註冊協議 (RFC7591)。

  3. MCP 服務器應該和 MCP 客戶端必須實現 OAuth 2.0 鑑權服務器元數據協議 (RFC8414)。不支持元數據協議的服務器必須遵循默認 URI Schema。

OAuth 授權類型

OAuth 指定不同的流或授權類型,這是獲得訪問令牌的不同方式。每個目標都有不同的用例和場景。

MCP 服務器應該支持 OAuth 授權類型,這種授權類型最適合目標用戶。例如:

  1. 鑑權碼: 當客戶短代表 (人類) 最終用戶行事時非常有用。

    • 例如,Agent 調用由 SaaS 系統實現的 MCP 工具。
  2. 客戶端憑據: 客戶端是另一個應用程序 (不是人)

    • 例如,Agent 調用一個安全 MCP 工具來檢查特定商店的庫存, 不需要模擬最終用戶。

4.4.2.2 示例: 鑑權碼授予

這裏演示了用於用戶身份驗證的鑑權碼授予類型的 OAuth 2.1 流。

注意: 下面的示例假定 MCP 服務器也作爲授權服務器運行。但是,可以將授權服務器部署爲其自己的特定服務。

人類用戶通過 web 瀏覽器完成 OAuth 流程,獲得一個訪問令牌,該令牌可以識別用戶,並允許客戶端代表用戶進行操作。

當需要鑑權且客戶端尚未證明授權時,服務器必須響應 HTTP 401 Unauthorized。

客戶端在收到 HTTP 401 Unauthorized 之後啓動 OAuth 2.1 IETF DRAFT 鑑權流程。

下圖展示了使用 PKCE 公共客戶端的基本 OAuth 2.1 流程。

4.4.2.3 服務器元數據發現

對於服務器能力發現而言:

發現流程如下:

4.4.2.3.1 服務器元數據發現的 HTTP 頭

MCP 客戶端應該在服務器元數據發現期間包含頭 MCP-protocol-version: ,以允許 MCP 服務器基於 MCP 的協議版本進行響應。

例如: MCP-Protocol-Version: 2024-11-05

4.4.2.3.2 鑑權的基 URL

通過丟棄任何當前的路徑元素,鑑權的基 URL 必須從 MCP 服務器 URL 中確定。例如:

如果 MCP 服務器 URL 是 https://api.example.com/v1/MCP ,那麼:

這確保鑑權端點始終位於承載 MCP 服務器的域名的根級別,而不管 MCP 服務器 URL 中的其他路徑元素如何。

4.4.2.3.3 服務器未支持元數據發現的的後備方案

對於沒有實現 OAuth 2.0 Authorization Server Metadata 協議的服務器,客戶端必須使用相對於鑑權的基 URL (在 2.3.2 節中定義) 的以下默認端點路徑:

tSa5Fk

例如,當 MCP 服務器託管在 https://api.example.com/v1/MCP 時,默認端點爲:

https://api.example.com/authorize
https://api.example.com/token
https://api.example.com/register

客戶端必須首先嚐試通過元數據文檔發現端點,然後再回到默認路徑。當使用默認路徑時,所有其他協議要求保持不變。

4.4.2.4 動態客戶端註冊

MCP 客戶端和服務器應該支持 OAuth 2.0 動態客戶端註冊協議,以允許 MCP 客戶端在沒有用戶交互的情況下獲得 OAuth 客戶端 ID。這爲客戶端自動向新服務器註冊提供了一種標準化的方法,對於 MCP 至關重要,因爲:

任何不支持動態客戶端註冊的 MCP 服務器都需要提供獲取客戶端 ID 以及 (如果適用的話) 客戶端保密的替代方法。對於其中一臺服務器,MCP 客戶端必須滿足以下條件之一:

  1. 專門爲 MCP 服務器硬編碼客戶端 ID (如果適用,還有客戶端密鑰) ,或者

  2. 在註冊 OAuth 客戶端之後 ,爲用戶提供一個允許他們輸入這些細節的 UI(例如,通過服務器託管的配置接口)。

4.4.2.5 鑑權的流程步驟

完整的鑑權流程如下:

4.4.2.5.1 決策流程概述

4.4.2.6 訪問令牌的使用

4.4.2.6.1 令牌要求

訪問令牌的處理必須符合 OAuth 2.1 第 5 部分對資源請求的要求,特別是:

  1. MCP 客戶端必須使用 OAuth 2.1 中 5.1.1 節的鑑權請求頭字段:
Authorization: Bearer <access-token>

請注意,從客戶端到服務器的每個 HTTP 請求中都必須包含鑑權,即使它們是同一邏輯會話的一部分。

  1. 訪問令牌不能包含在 URI 的查詢字符串中 請求示例:
GET /v1/contexts HTTP/1.1
Host: mcp.example.com
Authorization: Bearer eyJhbGciOiJIUzI1NiIs...
4.4.2.6.2 令牌處理

資源服務器必須驗證訪問令牌,如 OAuth 2.1 的第 5.2 節所述。如果驗證失敗,服務器必須根據 5.3 節的錯誤處理要求進行響應。無效或過期的令牌必須接收一個 HTTP 401 響應。

4.4.2.7 安全性考量

必須執行下列安全性要求:

4.4.2.8 錯誤處理

服務器必須爲鑑權錯誤返回適當的 HTTP 狀態碼:

bQL0fO

4.4.2.9 實施規定

  1. 具體實現必須遵循 OAuth 2.1 安全最佳實踐

  2. 所有客戶端都需要 PKCE

  3. 爲了增強安全性,應該實現令牌輪換

  4. 令牌生存週期應該根據安全需求進行限制

4.4.2.10 第三方鑑權流程

4.4.2.10.1 概覽

MCP 服務器可以通過第三方鑑權服務器支持委託鑑權。在這個流程中,MCP 服務器既充當 OAuth 客戶端 (對於第三方身份驗證服務器) ,又充當 OAuth 鑑權服務器 (對於 MCP 客戶端)。

4.4.2.10.2 流程描述

第三方鑑權流程包括以下步驟:

  1. MCP 客戶端與 MCP 服務器初始化標準 OAuth 流程

  2. MCP 服務器將用戶請求重定向到第三方鑑權服務器

  3. 使用第三方服務器進行用戶授權

  4. 第三方服務器使用鑑權重定向回 MCP 服務器

  5. MCP 服務器爲第三方訪問令牌交換鑑權碼

  6. MCP 服務器生成自己綁定到第三方會話的訪問令牌

  7. MCP 服務器使用 MCP 客戶端完成初始的 OAuth 流程

4.4.2.10.3 會話綁定要求

實現第三方授權的 MCP 服務器必須:

  1. 維護第三方令牌與已發佈 MCP 令牌之間的安全映射

  2. 在承認 MCP 令牌之前驗證第三方令牌的狀態

  3. 實現適當的令牌生命週期管理

  4. 處理第三方令牌的過期和更新

4.4.2.10.4 安全性考量

在實施第三方授權時,服務器必須:

  1. 驗證所有重定向 URI

  2. 安全地存儲第三方憑據

  3. 實現適當的會話超時處理

  4. 考慮令牌鏈的安全性影響

  5. 爲第三方身份鑑權失敗實現正確的錯誤處理

4.4.3 最佳實踐

4.4.3.1 本地客戶端作爲公共 OAuth 2.1 客戶端

我們強烈建議本地客戶端將 OAuth 2.1 作爲公共客戶端實現:

  1. 對鑑權請求使用 PKCE 以防止攔截攻擊

  2. 實現適合本地系統的安全令牌存儲

  3. 遵循令牌刷新的最佳實踐來維護會話

  4. 正確處理令牌的過期和更新  

4.4.3.2 鑑權元數據的發現

我們強烈建議所有客戶端都實現元數據發現。這減少了用戶手動提供端點或客戶端回退到預定義默認值的需要。

4.4.3.3 動態客戶端註冊

由於客戶端事先不知道 MCP 服務器的集合,我們強烈建議實現動態客戶端註冊。這允許應用程序自動向 MCP 服務器註冊,並消除了用戶手動獲取客戶機 id 的需要。

4.5 實用程序

4.5.1 取消請求

模型上下文協議支持通過通知消息可選地取消正在進行的請求。任何一方都可以發送取消通知,表明以前發出的請求應該終止。

4.5.1.1 取消流程

當一方希望取消一個正在進行的請求時,它會發送一個 notifications/cancelled 通知,其中包括:

{
  "jsonrpc": "2.0",
  "method": "notifications/cancelled",
  "params": {
    "requestId": "123",
    "reason": "User requested cancellation"
  }
}

4.5.1.2 行爲要求

  1. 取消通知必須只有請求:

    • 先前已向同一方向發出

    • 確信仍在進行中

  2. 客戶端不能取消初始化請求

  3. 取消通知的接收方應該:

    • 停止處理取消的請求

    • 釋放相關資源

    • 不爲取消的請求發送響應

  4. 接收方可以忽略取消通知,如果:

    • 引用的請求未知

    • 處理工作已經完成

    • 請求無法取消

  5. 取消通知的發送方應該忽略對隨後到達請求的任何響應

4.5.1.3 時機的考量

由於網絡延遲,取消通知可能在請求處理完成之後到達,並且可能在響應已經發送之後到達。

雙方都必須妥善處理這些競爭條件:

4.5.1.4 實施說明

無效的取消通知應該被忽略:

這保持了通知的 “發送和忘記” 特性,同時允許異步通信中的競態條件。

4.5.2 Ping

模型上下文協議包含一個可選的 ping 機制,允許任何一方驗證對方是否仍然響應,以及連接是否存在。

4.5.2.1 概覽

Ping 功能是通過簡單的請求 / 響應模式實現的。客戶端或服務器都可以通過發送 ping 請求來初始化一個 ping。

4.5.2.2 消息格式

Ping 請求是一個沒有參數的標準 JSON-RPC 請求:

{
  "jsonrpc": "2.0",
  "id": "123",
  "method": "ping"
}

4.5.2.3 行爲要求

接收方必須立即作出一個空響應:

{ "jsonrpc": "2.0", "id": "123", "result": {} }
如果在合理的超時期限內沒有收到響應,則發送方可以:

4.5.2.4 使用模式

4.5.2.5 實現的考量

4.5.3 進度

模型上下文協議支持以通知消息對長時間運行的操作執行可選的進度跟蹤。任何一方都可以發送進度通知,以提供有關操作狀態的更新。

4.5.3.1 進度流程

當一方希望接收請求的進度更新時,它會在請求元數據中包含 progressToken。

        {
          "jsonrpc": "2.0",
          "id": 1,
          "method": "some_method",
          "params": {
            "_meta": {
              "progressToken": "abc123"
            }
          }
        }

然後,接收方可以發送進度通知,內容包括:

{
  "jsonrpc": "2.0",
  "method": "notifications/progress",
  "params": {
    "progressToken": "abc123",
    "progress": 50,
    "total": 100,
    "message": "Reticulating splines..."
  }
}

4.5.3.2 行爲要求

進度通知必須只引用以下令牌:

進度請求的接收方可以:

4.5.3.3 實施指南

5 客戶端特性

5.1 根目錄

模型上下文協議爲客戶端向服務器公開文件系統的 “根目錄” 提供了一種標準化的方法。Root 定義了服務器可以在文件系統中操作的邊界,允許服務器理解它們可以訪問哪些目錄和文件。服務器可以從支持的客戶端中請求根目錄的列表,並在該列表發生更改時接收通知。

5.1.1 用戶交互模型

MCP 中的根通常通過工作區或項目配置接口公開。

例如,實現可以提供一個工作區 / 項目選擇器,允許用戶選擇服務器應該訪問的目錄和文件。這可以與來自版本控制系統或項目文件的自動工作區檢測相結合。

然而,具體實現可以自由地通過任何符合其需要的接口模式來公開 “根”,協議本身並不要求任何特定的用戶交互模型。

5.1.2 能力

支持根目錄的客戶端必須在初始化期間聲明根目錄的能力:

{
  "capabilities": {
    "roots": {
      "listChanged": true
    }
  }
}

listChanged 指示當根列表發生更改時,客戶端是否發出通知。

5.1.3 協議消息

5.1.3.1 Listing Roots

爲了檢索根目錄,服務器發送一個 roots/list 請求。

請求:

{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "roots/list"
}

響應:

{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "roots": [
      {
        "uri": "file:///home/user/projects/myproject",
        "name": "My Project"
      }
    ]
  }
}

5.1.3.2 Root List 變更

當根發生變更時,支持 listChanged 的客戶端必須發送一個通知。

{
        "jsonrpc": "2.0",
"method": "notifications/roots/list_changed"
}

5.1.4 消息流程

5.1.5 數據類型

5.1.5.1 Root

根的定義包括:

URI: root 的唯一標識符,必須是當前規範中的文件://URI。
名稱:用於顯示目的的人類可讀名稱 (可選)。

不同用例的 root 示例:

項目目錄
{
  "uri": "file:///home/user/projects/myproject",
  "name": "My Project"
}
多儲存庫
[
  {
    "uri": "file:///home/user/repos/frontend",
    "name": "Frontend Repository"
  },
  {
    "uri": "file:///home/user/repos/backend",
    "name": "Backend Repository"
  }
]

5.1.6 錯誤處理

對於常見的失敗情況,客戶端應該返回標準的 JSON-RPC 錯誤:

錯誤示例:

{
  "jsonrpc": "2.0",
  "id": 1,
  "error": {
    "code": -32601,
    "message": "Roots not supported",
    "data": {
      "reason": "Client does not have roots capability"
    }
  }
}

5.1.7 安全事宜

  1. 客戶端必須:
  1. 服務器應該:

5.1.8 實施指南

客戶端應該:

服務器應該:

5.2 採樣

模型上下文協議爲服務器通過客戶端從語言模型請求 LLM 採樣 (“補全” 或 “代替”) 提供了一種標準化的方法。此流程允許客戶端維護對模型訪問、選擇和權限的控制,同時允許服務器利用 AI 功能ーー不需要服務器 API 密鑰。服務器可以請求基於文本、音頻或圖像的交互,還可以在提示詞中包含來自 MCP 服務器的上下文。

5.2.1 用戶交互模型

MCP 中的採樣允許服務器實現智能體行爲,允許 LLM 調用嵌套在其他 MCP 服務器的功能。

具體實現可以自由地通過任何適合其需要的接口模式公開採樣,協議本身並不要求任何特定的用戶交互模型。

爲了信任、保密和安全性,應該總是有一個人工行爲在循環中有能力拒絕採樣請求。

應用應該:

支持採樣的客戶端必須在初始化期間聲明採樣能力:

{
  "capabilities": {
    "sampling": {}
  }
}

5.2.3 協議消息

5.2.3.1 創建消息

爲了請求語言模型的一個生成結果,服務器發送一個 sampling/createMessage 請求:

請求:

{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "sampling/createMessage",
  "params": {
    "messages": [
      {
        "role": "user",
        "content": {
          "type": "text",
          "text": "What is the capital of France?"
        }
      }
    ],
    "modelPreferences": {
      "hints": [
        {
          "name": "claude-3-sonnet"
        }
      ],
      "intelligencePriority": 0.8,
      "speedPriority": 0.5
    },
    "systemPrompt": "You are a helpful assistant.",
    "maxTokens": 100
  }
}

響應:

{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "role": "assistant",
    "content": {
      "type": "text",
      "text": "The capital of France is Paris."
    },
    "model": "claude-3-sonnet-20240307",
    "stopReason": "endTurn"
  }
}

5.2.4 消息流程

5.2.5 數據類型

5.2.5.1 消息

採樣信息可以包含:

文字內容
{
  "type": "text",
  "text": "The message content"
}
圖片內容
{
  "type": "image",
  "data": "base64-encoded-image-data",
  "mimeType": "image/jpeg"
}
音頻內容
{
  "type": "audio",
  "data": "base64-encoded-audio-data",
  "mimeType": "audio/wav"
}

5.2.6 模型偏好設置

MCP 中的模型選擇需要仔細的抽象,因爲服務器和客戶端可能使用不同的 AI 提供者提供不同的模型。服務器不能簡單地通過名稱請求特定的模型,因爲客戶端可能無法訪問該確切的模型,或者可能更喜歡使用不同提供者的等價模型。

爲了解決這個問題,MCP 實現了一個偏好設置系統,將抽象的能力優先級與可選的模型引導結合起來。

5.2.6.1 能力優先級

服務器通過三個規範化的優先級值 (0-1) 來表達它們的需求:

5.2.6.2 模型引導

雖然優先級有助於根據特徵選擇模型,但引導允許服務器建議特定的模型或模型家族:

例如:

{
  "hints": [
    { "name": "claude-3-sonnet" }, // Prefer Sonnet-class models
    { "name": "claude" } // Fall back to any Claude model
  ],
  "costPriority": 0.3, // Cost is less important
  "speedPriority": 0.8, // Speed is very important
  "intelligencePriority": 0.5 // Moderate capability needs
}

客戶端處理這些偏好項以從其可用選項中選擇適當的模型。例如,如果客戶端沒有訪問 Claude 模型,但有 Gemini,它可能會基於類似的功能將 sonnet 引導映射到 Gemini-1.5-pro。

5.2.7 錯誤處理

對於常見的故障情況,客戶端應該返回錯誤:

錯誤示例:

{
  "jsonrpc": "2.0",
  "id": 1,
  "error": {
    "code": -1,
    "message": "User rejected sampling request"
  }
}

5.2.7 安全事宜

  1. 客戶端應實現用戶審批控制

  2. 雙方都應該驗證消息內容

  3. 客戶端應該遵循模型的偏好引導

  4. 客戶端應實施速率限制

  5. 雙方必須適當地處理敏感數據

6. 服務器特性

6.1 概覽

服務器提供了通過 MCP 向語言模型添加上下文的基本構建塊。這些原語支持客戶端、服務器和語言模型之間的豐富交互:

每個原語可以歸納爲以下的控制層次結構:

2QP9mQ

以下更詳細地探討這些關鍵原語:提示詞、資源和工具。

6.2 提示詞

模型上下文協議 (Model Context Protocol,MCP) 爲服務器向客戶機公開提示模板提供了一種標準化的方法。提示允許服務器提供與語言模型交互的結構化消息和指令。客戶機可以發現可用的提示,檢索它們的內容,並提供參數來定製它們。

6.2.1 用戶交互模型

提示詞被設計爲由用戶控制,這意味着它們從服務器公開給客戶端,用戶可以顯式地選擇它們來使用。

通常,提示詞將通過用戶界面中由用戶發起的命令觸發,這允許用戶自然地發現和調用可用的提示次。例如,作爲斜槓命令。

然而,實現者可以自由地通過任何適合他們需要的接口模式公開提示詞ーー協議本身並不要求任何特定的用戶交互模型。

6.2.2 能力

支持提示詞的服務器必須在初始化期間聲明提示詞功能:

{
  "capabilities": {
    "prompts": {
      "listChanged": true
    }
  }
}

listChanged 指示了當可用提示詞列表發生更改時,服務器是否發出通知。

6.2.3 協議消息

6.2.3.1 對提示詞進行檢索

爲了檢索可用的提示詞,客戶端發送一個 prompts/list 請求。此操作支持分頁。

請求:

{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "prompts/list",
  "params": {
    "cursor": "optional-cursor-value"
  }
}

響應:

{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "prompts": [
      {
        "name": "code_review",
        "description": "Asks the LLM to analyze code quality and suggest improvements",
        "arguments": [
          {
            "name": "code",
            "description": "The code to review",
            "required": true
          }
        ]
      }
    ],
    "nextCursor": "next-page-cursor"
  }
}

6.2.3.2 獲得提示詞

爲了檢索特定的提示詞,客戶端發送一個 prompts/get 請求。參數可以通過完整的 API 自動完成。

請求:

{
  "jsonrpc": "2.0",
  "id": 2,
  "method": "prompts/get",
  "params": {
    "name": "code_review",
    "arguments": {
      "code": "def hello():\n    print('world')"
    }
  }
}

響應:

{
  "jsonrpc": "2.0",
  "id": 2,
  "result": {
    "description": "Code review prompt",
    "messages": [
      {
        "role": "user",
        "content": {
          "type": "text",
          "text": "Please review this Python code:\ndef hello():\n    print('world')"
        }
      }
    ]
  }
}

6.2.3.3 變更通知

當可用提示詞列表發生更改時,聲明 listChanged 能力的服務器應發送通知:

{
  "jsonrpc": "2.0",
  "method": "notifications/prompts/list_changed"
}

6.2.4 消息流

6.2.5 數據類型

6.2.5.1 提示詞

一個提示詞的定義包括:

一個提示詞中的消息可以包含:

角色:指代說話者是 “用戶” 或 “助手”
內容:以下內容類型之一:

文字內容

文本內容表示純文本消息:

{
  "type": "text",
  "text": "The text content of the message"
}

這是用於自然語言交互的最常見內容類型。

圖片內容

圖像內容允許在消息中包含視覺信息:

{
  "type": "image",
  "data": "base64-encoded-image-data",
  "mimeType": "image/png"
}

圖像數據必須是 base64 編碼,並且包含有效的 MIME 類型。這使得多模態交互在視覺上下文很重要的地方成爲可能。

音頻內容

音頻內容允許在消息中包含音頻信息:

{
  "type": "audio",
  "data": "base64-encoded-audio-data",
  "mimeType": "audio/wav"
}

音頻數據必須是 base64 編碼,並且包含有效的 MIME 類型。這使得在音頻上下文很重要的情況下進行多模態交互成爲可能。

嵌入式資源

嵌入式資源允許在消息中直接引用服務器端資源:

{
  "type": "resource",
  "resource": {
    "uri": "resource://example",
    "mimeType": "text/plain",
    "text": "Resource content"
  }
}

資源可以包含文本或二進制 (blob) 數據,必須包括:

嵌入式資源允許提示詞將服務器管理的內容 (如文檔、代碼示例或其他參考資料) 無縫地直接合併到會話流中。

6.2.6 錯誤處理

對於常見的故障情況,服務器應該返回標準的 JSON-RPC 錯誤:

  1. 服務器在處理前驗證提示參數

  2. 客戶端應該處理大型提示詞列表的分頁

  3. 雙方應該遵循能力協商 

6.2.8 安全性

具體實現必須仔細驗證所有提示詞的輸入和輸出,以防止注入攻擊或未經授權的資源訪問。

6.3 資源

模型上下文協議爲服務器向客戶端公開資源提供了一種標準化的方法。資源允許服務器共享爲語言模型提供上下文的數據,例如文件、數據庫模式或特定於應用程序的信息。每個資源都由一個 URI 唯一標識。

6.3.1 用戶交互模型

MCP 中的資源被設計爲由應用程序所驅動,由主機應用程序根據自己的需要確定如何合併上下文。

例如,應用程序可以:

然而,具體實現可以通過任何適合其需要的接口模式自由地公開資源ーー協議本身並不強制任何特定的用戶交互模型。

6.3.3 能力

支持資源的服務器必須聲明資源能力:

{
  "capabilities": {
    "resources": {
      "subscribe": true,
      "listChanged": true
    }
  }
}

該能力支持兩個可選特性:

Subscribe 和 listChanged 都是可選的ーー服務器可以不支持它們,也可以支持它們中的一個,或者兩者都支持:

{
  "capabilities": {
    "resources": {} // Neither feature supported
  }
}


{
  "capabilities": {
    "resources": {
      "subscribe": true // Only subscriptions supported
    }
  }
}


{
  "capabilities": {
    "resources": {
      "listChanged": true // Only list change notifications supported
    }
  }
}

6.3.4 協議消息

6.3.4.1 資源的檢索

爲了發現可用的資源,客戶端發送一個 resources/list 請求。此操作支持分頁。

請求:

{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "resources/list",
  "params": {
    "cursor": "optional-cursor-value"
  }
}

響應:

{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "resources": [
      {
        "uri": "file:///project/src/main.rs",
        "name": "main.rs",
        "description": "Primary application entry point",
        "mimeType": "text/x-rust"
      }
    ],
    "nextCursor": "next-page-cursor"
  }
}

6.3.4.2 讀取資源

爲了檢索資源內容,客戶端發送一個 resources/read 請求。

請求:

{
  "jsonrpc": "2.0",
  "id": 2,
  "method": "resources/read",
  "params": {
    "uri": "file:///project/src/main.rs"
  }
}

響應:

{
  "jsonrpc": "2.0",
  "id": 2,
  "result": {
    "contents": [
      {
        "uri": "file:///project/src/main.rs",
        "mimeType": "text/x-rust",
        "text": "fn main() {\n    println!(\"Hello world!\");\n}"
      }
    ]
  }
}

6.3.4.3 資源模板

資源模板允許服務器使用 URI 模板公開參數化的資源。參數可以通過 API 自動補全。

請求:

{
  "jsonrpc": "2.0",
  "id": 3,
  "method": "resources/templates/list"
}

響應:

{
  "jsonrpc": "2.0",
  "id": 3,
  "result": {
    "resourceTemplates": [
      {
        "uriTemplate": "file:///{path}",
        "name": "Project Files",
        "description": "Access files in the project directory",
        "mimeType": "application/octet-stream"
      }
    ]
  }
}

6.3.4.4 名單更改通知

當可用資源列表發生更改時,聲明 listChanged 功能的服務器應發送通知。

{
  "jsonrpc": "2.0",
  "method": "notifications/resources/list_changed"
}

6.3.4.5 訂閱

該協議支持對資源更改的可選訂閱。客戶端可以訂閱特定的資源,並在資源更改時接收通知。

訂閱請求:

{
  "jsonrpc": "2.0",
  "id": 4,
  "method": "resources/subscribe",
  "params": {
    "uri": "file:///project/src/main.rs"
  }
}

更新通知:

{
  "jsonrpc": "2.0",
  "method": "notifications/resources/updated",
  "params": {
    "uri": "file:///project/src/main.rs"
  }
}

6.3.5 消息流程

6.3.6 數據類型

6.3.6.1 資源

一個資源定義包括:

資源可以包含文本數據或二進制數據:

文字內容
{
  "uri": "file:///example.txt",
  "mimeType": "text/plain",
  "text": "Resource content"
}
二進制內容
{
  "uri": "file:///example.png",
  "mimeType": "image/png",
  "blob": "base64-encoded-data"
}

6.3.6.3 常見的 URI 方案

該協議定義了幾個標準的 URI 模式。這個列表並不詳盡,具體實現總是可以自由地使用額外的、自定義的 URI 模式。

https://

用於表示 web 上可用的資源。

只有當客戶端能夠自己直接從 web 獲取和加載資源時,服務器才應該使用這種方案ーー也就是說,它不需要通過 MCP 服務器讀取資源。

對於其他用例,服務器應該優先使用另一個 URI 方案,或者定義一個自定義 URI 方案,即使服務器本身將通過 internet 下載資源內容。

file://

用於標識行爲類似於文件系統的資源。但是,資源不需要映射到實際的物理文件系統。

MCP 服務器可以使用 XDG MIME 類型標識 file:// 資源,比如 inode/directory,來表示沒有標準 MIME 類型的非常規文件 (比如目錄)。

git://

Git 版本控制集成。

6.3.7 錯誤處理

對於常見的故障情況,服務器應該返回標準的 JSON-RPC 錯誤:

錯誤示例:

{
  "jsonrpc": "2.0",
  "id": 5,
  "error": {
    "code": -32002,
    "message": "Resource not found",
    "data": {
      "uri": "file:///nonexistent.txt"
    }
  }
}

6.3.8 安全事宜

  1. 服務器必須驗證所有資源的 URI

  2. 應對敏感資源實施訪問控制

  3. 二進制數據必須正確編碼

  4. 操作前應檢查資源權限

6.4 工具

模型上下文協議允許服務器公開可由語言模型調用的工具。工具使模型能夠與外部系統交互,例如查詢數據庫、調用 api 或執行計算。每個工具都由名稱唯一標識,幷包含描述其模式的元數據。

6.4.1 用戶交互模型

MCP 中的工具被設計爲由模型控制,這意味着語言模型可以根據其上下文理解和用戶的提示詞自動發現和調用工具。

然而,具體實現可以通過任何適合其需要的接口模式自由地公開工具ーー協議本身並不強制要求任何特定的用戶交互模型。

爲了信任、保密和安全性,在循環中應該始終有一個人工操控有能力拒絕工具調用。

應用應該:

支持工具的服務器必須聲明工具能力:

{
  "capabilities": {
    "tools": {
      "listChanged": true
    }
  }
}

listChanged 指示當可用工具列表發生更改時,服務器是否發出通知。

6.4.3 協議消息

6.4.3.1 對工具的檢索

爲了發現可用的工具,客戶端發送一個 tools/list 請求。這個操作支持分頁。

請求:

{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "tools/list",
  "params": {
    "cursor": "optional-cursor-value"
  }
}

響應:

{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "tools": [
      {
        "name": "get_weather",
        "description": "Get current weather information for a location",
        "inputSchema": {
          "type": "object",
          "properties": {
            "location": {
              "type": "string",
              "description": "City name or zip code"
            }
          },
          "required": ["location"]
        }
      }
    ],
    "nextCursor": "next-page-cursor"
  }
}

6.4.3.2 調用工具

要調用工具,客戶端發送一個 tools/call 請求:

請求:

{
  "jsonrpc": "2.0",
  "id": 2,
  "method": "tools/call",
  "params": {
    "name": "get_weather",
    "arguments": {
      "location": "New York"
    }
  }
}

響應:

{
  "jsonrpc": "2.0",
  "id": 2,
  "result": {
    "content": [
      {
        "type": "text",
        "text": "Current weather in New York:\nTemperature: 72°F\nConditions: Partly cloudy"
      }
    ],
    "isError": false
  }
}

6.4.3.3 更改通知

當可用工具列表發生更改時,聲明 listChanged 功能的服務器應該發送一個通知:

{
  "jsonrpc": "2.0",
  "method": "notifications/tools/list_changed"
}

6.4.4 消息流程

6.4.5 數據類型

6.4.5.1 工具

一個工具定義包括:

爲了信任、保密和安全性,客戶端必須認爲工具註釋是不可信的,除非它們來自受信任的服務器。

6.4.5.2 工具結果

工具結果可以包含不同類型的多個內容項:

文本內容
{
  "type": "text",
  "text": "Tool result text"
}
圖片內容
{
  "type": "image",
  "data": "base64-encoded-data",
  "mimeType": "image/png"
}
音頻內容
{
  "type": "audio",
  "data": "base64-encoded-audio-data",
  "mimeType": "audio/wav"
}
嵌入式資源

可以將資源嵌入到 URI 後面,以提供額外的上下文或數據,客戶端以後可以訂閱或再次獲取這些 URI:

{
  "type": "resource",
  "resource": {
    "uri": "resource://example",
    "mimeType": "text/plain",
    "text": "Resource content"
  }
}

6.4.6 錯誤處理

工具使用兩種錯誤報告機制。

6.4.6.1 協議錯誤

協議錯誤是 標準的 JSON-RPC 錯誤,例如:

協議錯誤示例:

{
  "jsonrpc": "2.0",
  "id": 3,
  "error": {
    "code": -32602,
    "message": "Unknown tool: invalid_tool_name"
  }
}

6.4.6.2 工具執行錯誤

工具執行錯誤在工具結果中使用 isError: true 報告:

工具執行錯誤示例:

{
  "jsonrpc": "2.0",
  "id": 4,
  "result": {
    "content": [
      {
        "type": "text",
        "text": "Failed to fetch weather data: API rate limit exceeded"
      }
    ],
    "isError": true
  }
}

6.4.7 安全事宜

1. 服務器必須:

2 客戶端應該:

6.5 實用程序

6.5.1 補全

模型上下文協議爲服務器提供了一種標準化的方法,用於爲提示詞和資源 uri 提供參數的自動補全建議。這使得用戶可以在輸入參數值時接收上下文建議,從而獲得豐富的類 ide 體驗。

6.5.1.1 用戶交互模型

MCP 中的補全設計用於支持類似於 IDE 代碼補全的交互式用戶體驗。

例如,當用戶輸入時,應用程序可以在下拉菜單或彈出菜單中顯示補全建議,並具有從可用選項中進行篩選和選擇的能力。

然而,具體實現可以自由地通過任何適合其需要的接口模式公開補全的能力,協議本身並不要求任何特定的用戶交互模型。

6.5.1.2 能力

支持補全的服務器必須聲明補全的能力:

{
  "capabilities": {
    "completions": {}
  }
}

6.5.1.3 協議消息

補全的請求

爲了獲得全建議,客戶端通過參考類型發送一個 completion/complete 請求,並指定正在完成的內容。

請求:

{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "completion/complete",
  "params": {
    "ref": {
      "type": "ref/prompt",
      "name": "code_review"
    },
    "argument": {
      "name": "language",
      "value": "py"
    }
  }
}

響應:

{
  "jsonrpc": "2.0",
  "id": 1,
  "result": {
    "completion": {
      "values": ["python", "pytorch", "pyside"],
      "total": 10,
      "hasMore": true
    }
  }
}
參考類型

該協議支持兩種類型的補全:

xtKW8s

完成結果

服務器返回一個按相關性排序的補全值的數組,其中包括:

6.5.1.4 消息流程

6.5.1.5 數據類型

CompleteRequest
CompleteResult

6.5.1.6 錯誤處理

錯誤處理 對於常見的故障情況,服務器應該返回標準的 JSON-RPC 錯誤:

6.5.1.7 實施考慮

  1. 服務器應該:

——按相關性排序返回建議
——在適當的地方實現模糊匹配
——補全請求速率限制
——驗證所有輸入

  1. 客戶端應該:

6.5.1.8 安全性

具體實施必須:

6.5.2 日誌

模型上下文協議爲服務器向客戶端發送結構化日誌消息提供了一種標準化方法。客戶端可以通過設置最低日誌級別來控制日誌記錄的詳細程度,服務器發送包含嚴重級別、可選日誌名稱和任意可序列化 json 數據的通知。

6.5.2.1 用戶交互模型

具體實現可以自由地通過任何符合其需要的接口模式公開日誌記錄,協議本身並不要求任何特定的用戶交互模型。

6.5.2.2 能力

發出日誌消息通知的服務器必須聲明日誌記錄能力:

{
  "capabilities": {
    "logging": {}
  }
}

6.5.2.3 日誌級別

該協議遵循 RFC 5424 規定的標準 syslog 的日誌嚴重級別:

JMgOOc

6.5.2.4 協議消息

設置日誌級別

要配置最低日誌級別,客戶端可以發送一個 logging/setLevel 請求 。

請求:

{
  "jsonrpc": "2.0",
  "id": 1,
  "method": "logging/setLevel",
  "params": {
    "level": "info"
  }
}
日誌消息通知

服務器使用 notifications/message 發送日誌消息:

{
  "jsonrpc": "2.0",
  "method": "notifications/message",
  "params": {
    "level": "error",
    "logger": "database",
    "data": {
      "error": "Connection failed",
      "details": {
        "host": "localhost",
        "port": 5432
      }
    }
  }
}

6.5.2.5 消息流程

6.5.2.6 錯誤處理

對於常見的故障情況,服務器應該返回標準的 JSON-RPC 錯誤:

1. 服務器應該:
2. 客戶可以:

6.5.2.8 安全性

1. 日誌消息不能包含:
2. 具體實現應該:

6.5.3 分頁

模型上下文協議支持可能返回大型結果集的分頁列表操作。分頁能夠允許服務器以更小的塊產生結果,而不是一次產生所有結果。

當通過互聯網連接到外部服務時,分頁尤其重要,而且對於本地集成也很有用,可以避免大型數據集的性能問題。

6.5.3.1 分頁模型

MCP 中的分頁使用不透明的基於遊標的方法,而不是編號頁。

當服務器發送包含以下內容的響應時,開始分頁:

接收到遊標後,客戶端可以通過發出包括該遊標在內的請求來繼續分頁:

{
  "jsonrpc": "2.0",
  "method": "resources/list",
  "params": {
    "cursor": "eyJwYWdlIjogMn0="
  }
}

6.5.3.4 分頁流程

6.5.3.5 支持分頁的操作

下列 MCP 操作支持分頁:

6.5.3.5 實施指引
1. 服務器應該:
2. 客戶應該
3. 客戶端必須將遊標視爲不透明的令牌:

7. 資源

7.1 版本控制

模型上下文協議使用符合 YYYY-MM-DD 格式的基於字符串的版本標識符,以指示向後不兼容更改的最後日期。

協議版本不會在協議更新時增加,只需更改保持向後兼容。這允許在保持互操作性的同時進行增量改進。

7.1.1 修訂版

修訂內容可標示如下:

Current 協議版本是 2025-03-26。

7.1.2 協商

版本協商發生在初始化過程中。客戶端和服務器可以同時支持多個協議版本,但是它們必須同意在會話中使用一個版本。

如果版本協商失敗,該協議提供適當的錯誤處理,允許客戶端在找不到與服務器兼容的版本時正常地終止連接。

本文由 Readfog 進行 AMP 轉碼,版權歸原作者所有。
來源https://mp.weixin.qq.com/s/buugkrhgixlb4n1Smcb80w