將代理連接到模型情境協定伺服器

使用 MCP 工具將您的 Foundry 代理連接到 模型上下文協定(MCP) 伺服器。 這種連結擴展了客服人員與外部工具與資料來源的能力。 透過連接遠端 MCP 伺服器端點,您的代理 Foundry 模型可存取由開發者及組織託管的工具,這些工具可由 MCP 相容客戶端如 Foundry Agent Service 使用。

MCP 是一個開放標準,定義應用程式如何向大型語言模型(LLM)提供工具與情境資料。 它能將外部工具整合到模型工作流程中,保持一致且可擴展。

提示

考慮用 工具箱來新增這個工具。 透過使用工具箱,你可以在代理與執行環境間重複使用該工具,並透過受管理的 MCP 端點集中管理憑證管理、版本管理與政策執行。 請參閱 工具箱快速入門。

在本文中,您將學習如何:

  • 新增遠端 MCP 伺服器作為工具。
  • 使用專案連線進行 MCP 伺服器的身份驗證。
  • 審查並核准 MCP 工具呼叫。
  • 排除常見的 MCP 整合問題。

如果你使用像 GitHub Copilot 這樣的程式代理程式,Microsoft Foundry 技能可以幫助設定 MCP 工具連線、認證、核准行為及故障排除步驟。

先決條件

開始前,請確保你具備:

  • 一個 Azure 訂閱,裡面有活躍的 Microsoft Foundry 專案。

  • Foundry 專案中的 Foundry 使用者角色,負責建立與測試代理。 如果為 MCP 驗證建立專案連線,您還需要該專案上的 Foundry 專案管理員角色。

    Important

    Foundry RBAC 角色最近已重新命名。 Foundry 用戶、Foundry 擁有者、Foundry Account Owner 以及 Foundry Project Manager 先前分別被稱為 Azure AI 使用者、Azure AI 擁有者、Azure AI 帳戶擁有者及 Azure AI Project 管理者。 在更名期間,你可能還會在某些地方看到之前的名字。角色 ID 與核心權限不會因命名而改變。

  • 這是你語言的最新 SDK 套件。 .NET SDK 目前處於預覽階段。 安裝詳情請參見 快速入門。

  • Azure憑證已配置以進行身份驗證(例如 DefaultAzureCredential)。

  • 存取遠端 MCP 伺服器端點(例如 GitHub 位於 https://api.githubcopilot.com/mcp 的 MCP 伺服器)。

選擇一項任務

任務 Path
連接代理程式並確認第一次成功的工具呼叫 遵循連接、核准、驗證及清理流程。
新增憑證或基於身份的存取權限 次要:設定認證。
連接至私人 MCP 端點 次要任務:檢視公共與私立端點的要求。
以背景模式執行耗時作業 次要任務:配置長期執行的操作。
了解串流與逾時行為 次要項目:檢視已知的限制。
設定伺服器選項或架設本地伺服器 次要:建立 MCP 連線 或 架設本地 MCP 伺服器。

關於 MCP 整合的概念細節,請參見 How it work。

使用支援

下表顯示 SDK 與設定對 MCP 連線的支援。

Microsoft Foundry 支援 Python SDK C# SDK JavaScript SDK Java 開發套件 REST API 基本代理設定 標準代理設定
✔️ ✔️ ✔️ ✔️ ✔️ ✔️ ✔️ ✔️

公用與私有 MCP 伺服器端點

代理服務支援公用與私有 MCP 伺服器端點:

  • 公開端點:連接任何公開可存取的遠端 MCP 伺服器。 此選項適用於 Basic 與 Standard 代理設定。
  • 私有端點:連接未暴露於公共網際網路的 MCP 伺服器。 私有 MCP 需要 設置私有網路 ,並在虛擬網路內設置專用的 MCP 子網。

若為私人 MCP 伺服器,請將 MCP 伺服器部署在 Azure 容器應用程式上,並使用僅限內部的輸入,部署於委派給 Microsoft.App/environments 的專用 MCP 子網路。 開始時,請使用 19-private-network-agents-tools-setup範本 ,該範本提供所需的網路基礎設施,包括 MCP 子網,或如果你不想自備資源,可以使用 11-private-network-basic-project 。

關於網路隔離環境中工具支援的詳細資訊,請參見 具備網路隔離的代理工具。

使用 Foundry 工具箱作為 MCP 端點

Foundry Toolbox 讓你能將多種工具——如網頁搜尋、程式碼解譯器、檔案搜尋、Azure AI 搜尋服務、MCP 伺服器、OpenAPI 工具以及代理對代理連線——整合到一個相容 MCP 的端點中。 與其在每個代理上分別設定每個工具,不如在 Foundry 中建立一個工具箱,並使用標準 mcp 工具設定(server_url 和 server_label)指向工具箱端點。

由於 Toolbox 端點相容於 MCP,任何能消耗 MCP 伺服器的執行環境也能同時消耗 Toolbox。 此相容性包括 Foundry Agent Service、Microsoft Agent Framework、LangGraph、GitHub Copilot SDK 及其他支援 MCP 的用戶端。 你可以在工具箱中新增、移除或重新設定工具,而不必更改你的代理程式碼。

關於設定步驟,請參見 「建立並使用鑄造廠工具箱」。

工具箱 MCP 端點支援透過 MCP 任務進行長期執行的操作,目前仍在預覽階段。 要使用長期執行的工具,請確保你的代理架構支援 MCP 任務。

工具箱 MCP 認證與設定

為您的 MCP 伺服器建立一個驗證類型符合您的情境的專案連線,然後在精簡的工具箱 YAML 中參考該連線。

步驟 1. 建立連線

匯出專案端點,並將其設為 `azd ai` 指令的目前作用中專案:

PROJECT_ENDPOINT="https://<account>.services.ai.azure.com/api/projects/<project>"
azd ai project set $PROJECT_ENDPOINT

選擇你需要的認證版本:

# No auth — public MCP server
azd ai connection create my-mcp-conn \
  --kind remote-tool \
  --target https://learn.microsoft.com/api/mcp \
  --auth-type none

# Custom-keys header (for example, GitHub PAT)
azd ai connection create my-mcp-conn \
  --kind remote-tool \
  --target https://api.githubcopilot.com/mcp/ \
  --auth-type custom-keys \
  --custom-key "Authorization=******"

# OAuth — Foundry-managed app
azd ai connection create my-mcp-conn \
  --kind remote-tool \
  --target https://api.githubcopilot.com/mcp \
  --auth-type oauth2 \
  --connector-name foundrygithubmcp

# OAuth — bring your own app registration
azd ai connection create my-mcp-conn \
  --kind remote-tool \
  --target https://your-mcp-server.example.com \
  --auth-type oauth2 \
  --authorization-url https://auth.example.com/authorize \
  --token-url https://auth.example.com/token \
  --client-id <oauth-client-id> \
  --client-secret <oauth-client-secret> \
  --scopes "<scope1> <scope2>"

# User Entra token (managed user identity passthrough; for example, Microsoft Fabric)
azd ai connection create my-mcp-conn \
  --kind remote-tool \
  --target https://api.fabric.microsoft.com/v1/mcp/fabricaihub/integrations/m365 \
  --auth-type user-entra-token \
  --audience https://analysis.windows.net/powerbi/api

# Project managed identity — the project's system-assigned MI
azd ai connection create my-mcp-conn \
  --kind remote-tool \
  --target https://<resource>.cognitiveservices.azure.com/language/mcp \
  --auth-type project-managed-identity \
  --audience https://cognitiveservices.azure.com

# Agentic identity — the agent's per-project identity
azd ai connection create my-mcp-conn \
  --kind remote-tool \
  --target https://<resource>.cognitiveservices.azure.com/language/mcp \
  --auth-type agentic-identity \
  --audience https://cognitiveservices.azure.com
--auth-type 其他旗幟
none —
custom-keys --custom-key "Header=Value" (可重複)
oauth2 --connector-name 用於由 Foundry 管理的 OAuth 應用程式,或 --authorization-url、--token-url、--client-secret、--client-id 和 --scopes 用於您自己的應用程式註冊
user-entra-token --audience <entra-audience>
project-managed-identity --audience <entra-audience> (選用)
agentic-identity --audience <entra-audience>

僅以下 MCP 伺服器支援由 Foundry 管理的 OAuth 應用程式。 將對應的值傳遞給 --connector-name。

MCP 伺服器 連接器名稱
Azure Databricks Genie foundrydatabricksmcp
GitHub foundrygithubmcp
Infobip WhatsApp MCP 伺服器 foundryinfobipmcp
Infobip RCS MCP 伺服器 foundryinfobiprcsmcp
Infobip SMS MCP 伺服器 foundryinfobipsmsmcp
LSEG 資料與分析 foundrylsegmcp
晨星 MCP 伺服器 foundrymorningstarmcp
Neon foundryneonmcp
Pipedream foundrypipedreammcp
Vercel foundryvercelmcp

對於其他啟用 OAuth 的 MCP 伺服器,請自行提供應用程式註冊。

對於以身分為基礎的驗證(user-entra-token、project-managed-identity、agentic-identity),請先在目標資源上將所需的 RBAC 角色指派給對應的主體,然後再呼叫工具箱。

步驟 2。 定義工具箱

# my-toolbox.yaml
description: MCP server tools
connections:
  - name: my-mcp-conn

步驟 3。 建立工具箱

azd ai toolbox create my-toolbox --from-file my-toolbox.yaml

使用者首次在專案中呼叫帶有 OAuth 基礎 MCP 的工具箱時,MCP 端點會回傳 CONSENT_REQUIRED 一個錯誤(代碼 -32006)並附上同意 URL:

{
  "error": {
    "code": -32006,
    "message": "User consent is required. Please visit: https://..."
  }
}

這種錯誤是預期中的。 在瀏覽器中開啟同意網址,完成 OAuth 授權流程,然後重新嘗試代理通話。 後續的通話都能成功,無需重複提示。

認證

次要路徑: 當 MCP 伺服器需要憑證或基於身份的存取時,請在首次成功路徑後設定認證。

許多 MCP 伺服器需要驗證。

在 Foundry Agent Service 中,使用專案連線來儲存認證細節,例如 API 金鑰或承載憑證,而非在應用程式中硬編碼憑證。

欲了解支援的認證選項,包括基於金鑰的Microsoft Entra身份及 OAuth 身份直通,請參閱 MCP server authentication。

註

設定 project_connection_id 為你專案連結的 ID。

提示

當你透過新增工具目錄新增 Azure DevOps MCP 伺服器時,你會在組織連線階段驗證 Azure DevOps,並將認證存為專案連線。 連接組織時,請使用最低權限存取,並檢閱範圍。

當你使用 Foundry Toolbox 的 MCP 端點時,工具箱會集中管理認證。 工具箱負責執行時對套件中所有工具的憑證注入、令牌更新及政策強制執行。 代理程式透過Microsoft Entra憑證(如 DefaultAzureCredential)來認證工具箱端點,且每個代理不需要傳遞個別工具憑證。 關於 Toolbox 認證設定,請參見 Toolbox 前置條件。

使用非微軟服務與伺服器的考量

當你使用連接的非 Microsoft 服務 服務時,你必須遵守與服務提供者之間的條款。 當你連接到非 Microsoft 服務時,你會將部分資料(例如提示內容)傳給非 Microsoft 服務,或者你的應用程式可能會從非 Microsoft 服務接收資料。 你對使用非 Microsoft 服務和資料,以及與此使用相關的任何費用負責。

您決定搭配本文所述 MCP 工具使用的遠端 MCP 伺服器,是由第三方建立,而非 Microsoft。 Microsoft 不會測試或驗證這些伺服器。 Microsoft 對於您使用任何遠端 MCP 伺服器,對您或其他人不負任何責任。

仔細檢視並追蹤你新增到 Foundry Agent Service 的 MCP 伺服器。 請依賴由可信賴服務提供者自行託管的伺服器,而非代理伺服器。

MCP 工具允許你傳遞遠端 MCP 伺服器可能需要的自訂標頭,例如認證金鑰或結構。 檢視所有與遠端 MCP 伺服器共享的資料,並記錄資料以供稽核。 要注意非 Microsoft 在資料保留和定位方面的做法。

註

Foundry 工具箱與第三方 MCP 伺服器不同。 工具箱是你在 Microsoft Foundry 專案中建立和管理的組織管理資源。 然而,在策展 Toolbox 內容時,你仍需負責工具選擇、資料處理及合規。

最佳實務

關於工具使用的一般指引,請參見 Microsoft Foundry Agent Service 中工具使用的最佳實務。

使用MCP伺服器時,請遵循以下做法:

  • 使用 allowed_tools 來使用工具允許清單。
  • 將工具描述、註解及遠端 MCP 伺服器的結果視為不可信輸入。 它們可以包含間接的提示注入指令。
  • 高風險作業,尤其是寫入資料或變更資源的工具,要求核准。
  • 在批准前,請先檢視所要求的工具名稱和論點。
  • 當伺服器的操作者、對外公開的工具或行為有所變更時,請檢查 allowed_tools、核准設定及連線權限。
  • 記錄核准與工具呼叫,以利稽核與疑難排解。

提示

當您透過 Add Tools 目錄新增 Azure DevOps MCP 伺服器時,工具選擇配置會對應本篇文章所述的 allowed_tools 行為。 在目錄介面中選擇工具子集,等同於在程式碼中指定一個 allowed_tools 清單。

首次成功路徑:連接、核准、驗證並清理

請使用你所選語言的 prompt-agent 範例。 當範例有代理類型標籤時,選擇 提示代理。 此路徑使第一次執行專注於一個任務:連接一台 MCP 伺服器、呼叫一個工具,並檢查結果。

  1. 連結: 將 MCP 工具設定為 require_approvalalways,並將其附加到代理程式。
  2. 批准: 執行範例,檢視所請求的伺服器、工具和參數,並只批准預期的呼叫。
  3. 請驗證: 確認最終回應包含 MCP 工具回傳的資訊,如預期輸出所示。
  4. 清理: 執行樣本的清理作業。 提示代理範例會刪除代理版本,而 TypeScript 範例也會刪除其對話。

用 Python 用 MCP 工具建立代理

請使用以下範例程式碼建立代理並呼叫函式。 .NET SDK 目前處於預覽階段。 詳情請參考 快速入門 。

以下範例展示了如何將 GitHub MCP 伺服器加入工具箱,並將工具箱附加到代理程式上。 選擇 Prompt Agents 以使用 Azure AI Projects SDK 建立伺服器端提示代理,或選擇 Hosted Agents 使用 Agent Framework FoundryChatClient 建立臨時且進行中的代理。

提示詞 Agent

import json
from azure.identity import DefaultAzureCredential
from azure.ai.projects import AIProjectClient
from azure.ai.projects.models import PromptAgentDefinition, MCPTool
from openai.types.responses.response_input_param import McpApprovalResponse, ResponseInputParam

# Format: "https://resource_name.ai.azure.com/api/projects/project_name"
PROJECT_ENDPOINT = "your_project_endpoint"
MCP_CONNECTION_NAME = "my-mcp-connection"

# Create clients to call Foundry API
project = AIProjectClient(
    endpoint=PROJECT_ENDPOINT,
    credential=DefaultAzureCredential(),
)
openai = project.get_openai_client()

# [START tool_declaration]
tool = MCPTool(
    server_label="api-specs",
    server_url="https://api.githubcopilot.com/mcp",
    require_approval="always",
    project_connection_id=MCP_CONNECTION_NAME,
)
# [END tool_declaration]

# Create a prompt agent with MCP tool capabilities
agent = project.agents.create_version(
    agent_name="MyAgent7",
    definition=PromptAgentDefinition(
        model="gpt-5-mini",
        instructions="Use MCP tools as needed",
        tools=[tool],
    ),
)
print(f"Agent created (id: {agent.id}, name: {agent.name}, version: {agent.version})")

# Create a conversation to maintain context across multiple interactions
conversation = openai.conversations.create()
print(f"Created conversation (id: {conversation.id})")

# Send initial request that will trigger the MCP tool
response = openai.responses.create(
    conversation=conversation.id,
    input="What is my username in my GitHub profile?",
    extra_body={"agent_reference": {"name": agent.name, "type": "agent_reference"}},
)

# Process any MCP approval requests that were generated
input_list: ResponseInputParam = []
for item in response.output:
    if item.type == "mcp_approval_request" and item.id:
        print("MCP approval requested")
        print(f"  Server: {item.server_label}")
        print(f"  Tool: {getattr(item, 'name', '<unknown>')}")
        print(
            f"  Arguments: {json.dumps(getattr(item, 'arguments', None), indent=2, default=str)}"
        )

        # Approve only after you review the tool call.
        # In production, implement your own approval UX and policy.
        should_approve = (
            input("Approve this MCP tool call? (y/N): ").strip().lower() == "y"
        )
        input_list.append(
            McpApprovalResponse(
                type="mcp_approval_response",
                approve=should_approve,
                approval_request_id=item.id,
            )
        )

# Send the approval response back to continue the agent's work
response = openai.responses.create(
    input=input_list,
    previous_response_id=response.id,
    extra_body={"agent_reference": {"name": agent.name, "type": "agent_reference"}},
)

print(f"Response: {response.output_text}")

# Clean up resources by deleting the agent version
project.agents.delete_version(agent_name=agent.name, agent_version=agent.version)
print("Agent deleted")

預期產出

以下範例顯示執行樣本時的預期輸出:

Agent created (id: <agent-id>, name: MyAgent7, version: 1)
Created conversation (id: <conversation-id>)
Response: Your GitHub username is "example-username".
Agent deleted

託管代理

此範例使用來自 Microsoft Agent Framework 的 FoundryChatClient,建立一個包含 GitHub MCP 伺服器的工具箱,然後使用 FoundryToolbox 將該工具箱端點附加到您的代管代理程式。 使用 pip install agent-framework-foundry 安裝套件,設定 FOUNDRY_PROJECT_ENDPOINT 和 FOUNDRY_MODEL 環境變數,然後使用 az login 登入。

import asyncio

from agent_framework import Agent
from agent_framework.foundry import FoundryChatClient, FoundryToolbox
from azure.ai.projects import AIProjectClient
from azure.ai.projects.models import MCPToolboxTool
from azure.identity import AzureCliCredential

PROJECT_ENDPOINT = "https://<account>.services.ai.azure.com/api/projects/<project>"
MCP_CONNECTION_NAME = "my-mcp-connection"


async def main() -> None:
    credential = AzureCliCredential()

    # 1. Add the GitHub MCP server to a toolbox.
    project = AIProjectClient(endpoint=PROJECT_ENDPOINT, credential=credential)
    server_tool = MCPToolboxTool(
        server_label="api-specs",
        server_url="https://api.githubcopilot.com/mcp",
        require_approval="always",
        project_connection_id=MCP_CONNECTION_NAME,
    )
    toolbox = project.toolboxes.create_version(
        name="mcp-server-toolbox",
        description="Toolbox with the GitHub MCP server",
        tools=[server_tool],
    )

    # 2. The toolbox exposes an MCP-compatible endpoint.
    TOOLBOX_MCP_URL = (
        f"{PROJECT_ENDPOINT}/toolboxes/{toolbox.name}"
        f"/versions/{toolbox.version}/mcp?api-version=v1"
    )

    # 3. Attach the toolbox to the hosted agent as an MCP tool.
,
        timeout=120.0,
    )

    toolbox_tool = FoundryToolbox(credential, url=TOOLBOX_MCP_URL)

agent = Agent(
        client=FoundryChatClient(credential=credential),
        instructions="You are a helpful assistant that uses your MCP tool "
        "to help with Microsoft documentation questions.",
        tools=[toolbox_tool],
    )

    result = await agent.run("What is Microsoft Agent Framework?")
    print(f"Agent: {result.text}")

if __name__ == "__main__":
    asyncio.run(main())

預期產出

代理程式透過工具箱端點呼叫 Microsoft Learn MCP 伺服器,並回傳基於文件的文字:

Agent: Microsoft Agent Framework is an open-source framework for building, orchestrating, and deploying AI agents ...

如需完整的託管代理工具箱模式,請參閱 「使用工具箱搭配託管代理」。


使用 MCP 工具建立代理人

以下範例說明如何將遠端 MCP 伺服器加入工具箱,並將工具箱附加到代理程式。 選擇 Prompt Agents 以使用 Azure AI Projects SDK 建立伺服器端提示代理,或選擇 Hosted Agents 使用 Microsoft 代理框架建立一個短暫且進行中的代理。

提示詞 Agent

範例使用同步方法來建立代理。 關於非同步方法,請參閱GitHub .NET 倉庫Azure SDK中的 sample code。

using System;
using Azure.AI.Projects;
using Azure.AI.Extensions.OpenAI;
using Azure.Identity;

// Format: "https://resource_name.ai.azure.com/api/projects/project_name"
var projectEndpoint = "your_project_endpoint";

// Create project client to call Foundry API
AIProjectClient projectClient = new(
    endpoint: new Uri(projectEndpoint),
    tokenProvider: new DefaultAzureCredential());

// Create Agent with the `MCPTool`. Note that in this scenario 
// GlobalMcpToolCallApprovalPolicy.AlwaysRequireApproval is used,
// which means that any calls to the MCP server must be approved.
DeclarativeAgentDefinition agentDefinition = new(model: "gpt-5-mini")
{
    Instructions = "You are a helpful agent that can use MCP tools to assist users. Use the available MCP tools to answer questions and perform tasks.",
    Tools = { ResponseTool.CreateMcpTool(
        serverLabel: "api-specs",
        serverUri: new Uri("https://gitmcp.io/Azure/azure-rest-api-specs"),
        toolCallApprovalPolicy: new McpToolCallApprovalPolicy(GlobalMcpToolCallApprovalPolicy.AlwaysRequireApproval
    )) }
};
AgentVersion agentVersion = projectClient.AgentAdministrationClient.CreateAgentVersion(
    agentName: "myAgent",
    options: new(agentDefinition));

// If the tool approval is required, the response item is
// of `McpToolCallApprovalRequestItem` type and contains all
// the information about tool call. This example checks that
// the server label is "api-specs" and approves the tool call.
// All other calls are denied because they should not occur for
// the current configuration.
ProjectResponsesClient responseClient = projectClient.ProjectOpenAIClient.GetProjectResponsesClientForAgent(agentVersion.Name);

CreateResponseOptions nextResponseOptions = new([ResponseItem.CreateUserMessageItem("Please summarize the Azure REST API specifications README")]);
ResponseResult latestResponse = null;

while (nextResponseOptions is not null)
{
    latestResponse = responseClient.CreateResponse(nextResponseOptions);
    nextResponseOptions = null;

    foreach (ResponseItem responseItem in latestResponse.OutputItems)
    {
        if (responseItem is McpToolCallApprovalRequestItem mcpToolCall)
        {
            nextResponseOptions = new CreateResponseOptions()
            {
                PreviousResponseId = latestResponse.Id,
            };
            if (string.Equals(mcpToolCall.ServerLabel, "api-specs"))
            {
                Console.WriteLine($"Approval requested for {mcpToolCall.ServerLabel} (tool: {mcpToolCall.ToolName})");
                Console.Write("Approve this MCP tool call? (y/N): ");
                bool approved = string.Equals(Console.ReadLine(), "y", StringComparison.OrdinalIgnoreCase);
                nextResponseOptions.InputItems.Add(ResponseItem.CreateMcpApprovalResponseItem(approvalRequestId: mcpToolCall.Id, approved: approved));
            }
            else
            {
                Console.WriteLine($"Rejecting unknown call {mcpToolCall.ServerLabel}...");
                nextResponseOptions.InputItems.Add(ResponseItem.CreateMcpApprovalResponseItem(approvalRequestId: mcpToolCall.Id, approved: false));
            }
        }
    }
}

// Output the final response from the agent.
Console.WriteLine(latestResponse.GetOutputText());

// Clean up resources by deleting the agent version.
projectClient.AgentAdministrationClient.DeleteAgentVersion(agentName: agentVersion.Name, agentVersion: agentVersion.Version);

預期產出

以下範例顯示執行樣本時的預期輸出:

Approval requested for api-specs...
Response: The Azure REST API specifications repository contains the OpenAPI specifications for Azure services. It is
organized by service and includes guidelines for contributing new specifications. The repository is intended for use by developers building tools and services that interact with Azure APIs.

託管代理

本範例會使用 Azure AI Projects SDK 建立 MCP 伺服器工具箱,然後透過 Microsoft Agent Framework AddFoundryToolboxes 整合,將工具箱中的工具提供給您託管的代理程式。 設定 AZURE_AI_PROJECT_ENDPOINT、AZURE_OPENAI_ENDPOINT 和 AZURE_AI_MODEL_DEPLOYMENT_NAME 環境變數,並使用 az login 登入。

using Azure.AI.AgentServer.Responses;
using Azure.AI.AgentServer.Responses.Models;
using Azure.AI.OpenAI;
using Azure.AI.Projects;
using Azure.AI.Extensions.OpenAI;
using Azure.Identity;
using Microsoft.Agents.AI;
using Microsoft.Agents.AI.Foundry.Hosting;
using Microsoft.Extensions.DependencyInjection;
using OpenAI.Chat;

string projectEndpoint = Environment.GetEnvironmentVariable("AZURE_AI_PROJECT_ENDPOINT")
    ?? "https://<account>.services.ai.azure.com/api/projects/<project>";
string openAiEndpoint = Environment.GetEnvironmentVariable("AZURE_OPENAI_ENDPOINT")
    ?? throw new InvalidOperationException("AZURE_OPENAI_ENDPOINT is not set.");
string deploymentName = Environment.GetEnvironmentVariable("AZURE_AI_MODEL_DEPLOYMENT_NAME") ?? "gpt-5-mini";

DefaultAzureCredential credential = new();

// 1. Create the MCP server tool and add it to a toolbox.
AIProjectClient projectClient = new(endpoint: new Uri(projectEndpoint), tokenProvider: credential);
McpTool mcpTool = ResponseTool.CreateMcpTool(
    serverLabel: "api-specs",
    serverUri: new Uri("https://gitmcp.io/Azure/azure-rest-api-specs"),
    toolCallApprovalPolicy: new McpToolCallApprovalPolicy(
        GlobalMcpToolCallApprovalPolicy.AlwaysRequireApproval));

ToolboxVersion toolboxVersion = projectClient.AgentAdministrationClient
    .GetAgentToolboxes().CreateToolboxVersion(
        toolboxName: "mcp-server-toolbox",
        tools: [ProjectsAgentTool.AsProjectTool(mcpTool)],
        description: "Toolbox with the GitHub MCP server");

// Create the hosted agent and register the toolbox integration.
AIAgent agent = projectClient.AsAIAgent(
    model: deploymentName,
    instructions: "You are a helpful assistant with access to the toolbox tools.",
    name: "hosted-toolbox-agent");

var builder = WebApplication.CreateBuilder(args);
builder.Services.AddFoundryResponses(agent);
builder.Services.AddFoundryToolboxes(credential, toolboxVersion.Name);

var app = builder.Build();
app.MapFoundryResponses();
app.Run();

預期產出

當被啟動時,託管代理會透過工具箱端點向 Microsoft Learn MCP 伺服器查詢文件摘要與答案:

User: How does one create an Azure storage account using the az CLI?

Agent: To create an Azure storage account using the az CLI, run: `az storage account create --name <name> --resource-group <rg> --location <region> --sku Standard_LRS` ...

關於維護的 .NET 代理框架整合,請參見「使用工具箱搭配託管代理」。


使用 MCP 工具建立代理程式,並搭配專案連線認證

在這個例子中,你會學習如何在工具箱內驗證 GitHub MCP 伺服器,然後將工具箱的 MCP 端點附加到代理程式上。 範例使用同步方法來建立工具箱與代理。 關於非同步方法,請參閱GitHub .NET 倉庫Azure SDK中的 sample code。

建立專案連線

在執行樣本之前:

  1. 登入你的 GitHub 個人檔案。
  2. 請選擇右上角的個人頭像。
  3. 選擇 設定。
  4. 在左側面板,選擇開發者設定和個人存取令牌 > Tokens (classic)。
  5. 在最上方選擇 產生新代幣,輸入密碼,建立一個能讀取公開倉庫的代幣。
    • 重要: 儲存標記,或保持頁面開啟,因為一旦頁面關閉,標記就無法再顯示。
  6. 在 Azure 入口網站中,開啟 Microsoft Foundry。
  7. 在右上角的導覽中選擇「管理」,選擇「Project details」,然後選擇「已連接資源」標籤。
  8. 建立自訂 鍵 型的新連線。
  9. 為其命名並新增一個索引鍵值組。
  10. 將鍵名設為Authorization,並使值符合Bearer your_github_token的形式。

建立代理的程式碼範例

using System;
using Azure.AI.Projects;
using Azure.AI.Extensions.OpenAI;
using Azure.Identity;

// Format: "https://resource_name.ai.azure.com/api/projects/project_name"
var projectEndpoint = "your_project_endpoint";
var mcpConnectionName = "my-mcp-connection";

// Create project client to call Foundry API
AIProjectClient projectClient = new(
    endpoint: new Uri(projectEndpoint),
    tokenProvider: new DefaultAzureCredential());

// 1. Add the GitHub MCP server to a toolbox. Using a toolbox is the recommended
//    way to give agents tools. See /azure/foundry/agents/concepts/toolbox-overview
AgentToolboxes toolboxClient = projectClient.AgentAdministrationClient.GetAgentToolboxes();

McpTool mcpTool = ResponseTool.CreateMcpTool(
    serverLabel: "api-specs",
    serverUri: new Uri("https://api.githubcopilot.com/mcp"),
    toolCallApprovalPolicy: new McpToolCallApprovalPolicy(
        GlobalMcpToolCallApprovalPolicy.AlwaysRequireApproval));
mcpTool.ProjectConnectionId = mcpConnectionName;

ToolboxVersion toolboxVersion = toolboxClient.CreateToolboxVersion(
    toolboxName: "mcp-server-toolbox",
    tools: [ProjectsAgentTool.AsProjectTool(mcpTool)],
    description: "Toolbox with the GitHub MCP server");

// 2. The toolbox exposes an MCP-compatible endpoint.
var toolboxMcpUrl = new Uri(
    $"{projectEndpoint}/toolboxes/{toolboxVersion.Name}" +
    $"/versions/{toolboxVersion.Version}/mcp?api-version=v1");

// 3. Create a remote-tool project connection that points at the toolbox endpoint.
//    Use a user Entra token so the caller's identity is passed through
//    (audience https://ai.azure.com). Create the connection once, for example
//    with the Azure Developer CLI:
//
//    azd ai connection create mcp-server-toolbox-conn \
//      --kind remote-tool \
//      --target "<toolboxMcpUrl>" \
//      --auth-type user-entra-token \
//      --audience https://ai.azure.com
var toolboxConnectionName = "mcp-server-toolbox-conn";

// 4. Attach the toolbox to a prompt agent as an MCP tool. Note that in this scenario
//    GlobalMcpToolCallApprovalPolicy.AlwaysRequireApproval is used, which means that
//    any calls to the toolbox MCP endpoint must be approved.
McpTool toolboxTool = ResponseTool.CreateMcpTool(
    serverLabel: "toolbox",
    serverUri: toolboxMcpUrl,
    toolCallApprovalPolicy: new McpToolCallApprovalPolicy(
        GlobalMcpToolCallApprovalPolicy.AlwaysRequireApproval));
toolboxTool.ProjectConnectionId = toolboxConnectionName;

DeclarativeAgentDefinition agentDefinition = new(model: "gpt-5-mini")
{
    Instructions = "You are a helpful agent that can use MCP tools to assist users. Use the available MCP tools to answer questions and perform tasks.",
    Tools = { toolboxTool }
};
AgentVersion agentVersion = projectClient.AgentAdministrationClient.CreateAgentVersion(
    agentName: "myAgent",
    options: new(agentDefinition));

// If the tool approval is required, the response item is
// of McpToolCallApprovalRequestItem type and contains all
// the information about tool call. This example checks that
// the server label is "toolbox" and approves the tool call.
// All other calls are denied because they shouldn't happen given
// the current configuration.
ProjectResponsesClient responseClient = projectClient.ProjectOpenAIClient.GetProjectResponsesClientForAgent(agentVersion.Name);

CreateResponseOptions nextResponseOptions = new([ResponseItem.CreateUserMessageItem("What is my username in my GitHub profile?")]);
ResponseResult latestResponse = null;

while (nextResponseOptions is not null)
{
    latestResponse = responseClient.CreateResponse(nextResponseOptions);
    nextResponseOptions = null;

    foreach (ResponseItem responseItem in latestResponse.OutputItems)
    {
        if (responseItem is McpToolCallApprovalRequestItem mcpToolCall)
        {
            nextResponseOptions = new()
            {
                PreviousResponseId = latestResponse.Id,
            };
            if (string.Equals(mcpToolCall.ServerLabel, "toolbox"))
            {
                Console.WriteLine($"Approval requested for {mcpToolCall.ServerLabel} (tool: {mcpToolCall.ToolName})");
                Console.Write("Approve this MCP tool call? (y/N): ");
                bool approved = string.Equals(Console.ReadLine(), "y", StringComparison.OrdinalIgnoreCase);
                nextResponseOptions.InputItems.Add(ResponseItem.CreateMcpApprovalResponseItem(approvalRequestId: mcpToolCall.Id, approved: approved));
            }
            else
            {
                Console.WriteLine($"Rejecting unknown call {mcpToolCall.ServerLabel}...");
                nextResponseOptions.InputItems.Add(ResponseItem.CreateMcpApprovalResponseItem(approvalRequestId: mcpToolCall.Id, approved: false));
            }
        }
    }
}

// Output the final response from the agent.
Console.WriteLine(latestResponse.GetOutputText());

// Clean up resources by deleting the agent version.
projectClient.AgentAdministrationClient.DeleteAgentVersion(agentName: agentVersion.Name, agentVersion: agentVersion.Version);

預期產出

以下範例顯示執行樣本時的預期輸出:

Approval requested for toolbox...
Response: Your GitHub username is "example-username".

使用 MCP 工具在 TypeScript 中建立代理

以下 TypeScript 範例示範如何將 MCP 伺服器加入工具箱、將工具箱附加至代理程式、發送觸發 MCP 核准工作流程的請求、處理核准請求,以及清理資源。 關於 JavaScript 版本,請參閱 GitHub 上 JavaScript 倉庫Azure SDK上的 範例程式碼。

import { DefaultAzureCredential } from "@azure/identity";
import { AIProjectClient } from "@azure/ai-projects";
import OpenAI from "openai";
import * as readline from "readline";

// Format: "https://resource_name.ai.azure.com/api/projects/project_name"
const PROJECT_ENDPOINT = "your_project_endpoint";

export async function main(): Promise<void> {
  // Create clients to call Foundry API
  const project = new AIProjectClient(PROJECT_ENDPOINT, new DefaultAzureCredential());
  const openai = project.getOpenAIClient();

  console.log("Creating agent with MCP tool...");

  // 1. Add the Azure REST API specifications MCP server to a toolbox. Using a toolbox is
  //    the recommended way to give agents tools. See /azure/foundry/agents/concepts/toolbox-overview
  const toolbox = await project.toolboxes.createVersion(
    "mcp-server-toolbox",
    [
      {
        type: "mcp",
        server_label: "api-specs",
        server_url: "https://gitmcp.io/Azure/azure-rest-api-specs",
        require_approval: "always",
      },
    ],
    { description: "Toolbox with the Azure REST API specifications MCP server" },
  );

  // 2. The toolbox exposes an MCP-compatible endpoint.
  const toolboxMcpUrl =
    `${PROJECT_ENDPOINT}/toolboxes/${toolbox.name}` +
    `/versions/${toolbox.version}/mcp?api-version=v1`;

  // 3. Create a remote-tool project connection that points at the toolbox endpoint.
  //    Use a user Entra token so the caller's identity is passed through
  //    (audience https://ai.azure.com). Create the connection once, for example
  //    with the Azure Developer CLI:
  //
  //    azd ai connection create mcp-server-toolbox-conn \
  //      --kind remote-tool \
  //      --target "<toolboxMcpUrl>" \
  //      --auth-type user-entra-token \
  //      --audience https://ai.azure.com
  const toolboxConnectionName = "mcp-server-toolbox-conn";

  // 4. Attach the toolbox to a prompt agent as an MCP tool.
  // The toolbox tool requires approval for each operation to ensure user control over external requests.
  const agent = await project.agents.createVersion("agent-mcp", {
    kind: "prompt",
    model: "gpt-5-mini",
    instructions:
      "You are a helpful agent that can use MCP tools to assist users. Use the available MCP tools to answer questions and perform tasks.",
    tools: [
      {
        type: "mcp",
        server_label: "toolbox",
        server_url: toolboxMcpUrl,
        require_approval: "always",
        project_connection_id: toolboxConnectionName,
      },
    ],
  });
  console.log(`Agent created (id: ${agent.id}, name: ${agent.name}, version: ${agent.version})`);

  // Create a conversation thread to maintain context across multiple interactions
  console.log("\nCreating conversation...");
  const conversation = await openai.conversations.create();
  console.log(`Created conversation (id: ${conversation.id})`);

  // Send initial request that will trigger the MCP tool to access Azure REST API specs
  // This will generate an approval request since requireApproval="always"
  console.log("\nSending request that will trigger MCP approval...");
  const response = await openai.responses.create(
    {
      conversation: conversation.id,
      input: "Please summarize the Azure REST API specifications Readme",
    },
    {
      body: { agent_reference: { name: agent.name, type: "agent_reference" } },
    },
  );

  // Process any MCP approval requests that were generated
  // When requireApproval="always", the agent will request permission before accessing external resources
  const inputList: OpenAI.Responses.ResponseInputItem.McpApprovalResponse[] = [];

  const rl = readline.createInterface({ input: process.stdin, output: process.stdout });
  const ask = (q: string) => new Promise<string>((resolve) => rl.question(q, resolve));
  for (const item of response.output) {
    if (item.type === "mcp_approval_request") {
      if (item.server_label === "toolbox" && item.id) {
        console.log(`\nReceived MCP approval request (id: ${item.id})`);
        console.log(`  Server: ${item.server_label}`);
        console.log(`  Tool: ${item.name}`);

        // Approve only after you review the tool call.
        // In production, implement your own approval UX and policy.
        const answer = (await ask("Approve this MCP tool call? (y/N): ")).trim().toLowerCase();
        const approve = answer === "y";
        inputList.push({
          type: "mcp_approval_response",
          approval_request_id: item.id,
          approve,
        });
      }
    }
  }

  rl.close();

  console.log(`\nProcessing ${inputList.length} approval request(s)`);
  console.log("Final input:");
  console.log(JSON.stringify(inputList, null, 2));

  // Send the approval response back to continue the agent's work
  // This allows the MCP tool to access the GitHub repository and complete the original request
  console.log("\nSending approval response...");
  const finalResponse = await openai.responses.create(
    {
      input: inputList,
      previous_response_id: response.id,
    },
    {
      body: { agent_reference: { name: agent.name, type: "agent_reference" } },
    },
  );

  console.log(`\nResponse: ${finalResponse.output_text}`);

  // Clean up resources by deleting the agent version and conversation
  // This prevents accumulation of unused resources in your project
  console.log("\nCleaning up resources...");
  await openai.conversations.delete(conversation.id);
  console.log("Conversation deleted");

  await project.agents.deleteVersion(agent.name, agent.version);
  console.log("Agent deleted");

  console.log("\nMCP sample completed!");
}

main().catch((err) => {
  console.error("The sample encountered an error:", err);
});

預期產出

以下範例顯示執行樣本時的預期輸出:

Creating agent with MCP tool...
Agent created (id: <agent-id>, name: agent-mcp, version: 1)

Creating conversation...
Created conversation (id: <conversation-id>)

Sending request that will trigger MCP approval...

Received MCP approval request (id: <approval-request-id>)
  Server: api-specs
  Tool: get-readme

Processing 1 approval request(s)
Final input:
[
  {
    "type": "mcp_approval_response",
    "approval_request_id": "<approval-request-id>",
    "approve": true
  }
]

Sending approval response...

Response: The Azure REST API specifications repository contains the OpenAPI specifications for Azure services. It is organized by service and includes guidelines for contributing new specifications. The repository is intended for use by developers building tools and services that interact with Azure APIs.

Cleaning up resources...
Conversation deleted
Agent deleted

MCP sample completed!

使用 MCP 工具建立代理程式,並搭配專案連線認證

以下 TypeScript 範例示範如何將已認證的 MCP 伺服器加入工具箱、將工具箱 MCP 端點附加至代理程式、發送觸發 MCP 核准工作流程的請求、處理核准請求,以及清理資源。 關於 JavaScript 版本,請參閱 GitHub 上 JavaScript 倉庫Azure SDK上的 範例程式碼。

import { DefaultAzureCredential } from "@azure/identity";
import { AIProjectClient } from "@azure/ai-projects";
import OpenAI from "openai";
import * as readline from "readline";

// Format: "https://resource_name.ai.azure.com/api/projects/project_name"
const PROJECT_ENDPOINT = "your_project_endpoint";
const MCP_CONNECTION_NAME = "my-mcp-connection";

export async function main(): Promise<void> {
  // Create clients to call Foundry API
  const project = new AIProjectClient(PROJECT_ENDPOINT, new DefaultAzureCredential());
  const openai = project.getOpenAIClient();

  console.log("Creating agent with MCP tool using project connection...");

  // 1. Add the GitHub MCP server to a toolbox with project connection authentication.
  // The project connection should have Authorization header configured with "Bearer <GitHub PAT token>"
  // Token can be created at https://github.com/settings/personal-access-tokens/new
  const toolbox = await project.toolboxes.createVersion(
    "mcp-server-toolbox",
    [
      {
        type: "mcp",
        server_label: "api-specs",
        server_url: "https://api.githubcopilot.com/mcp",
        require_approval: "always",
        project_connection_id: MCP_CONNECTION_NAME,
      },
    ],
    { description: "Toolbox with the GitHub MCP server" },
  );

  // 2. The toolbox exposes an MCP-compatible endpoint.
  const toolboxMcpUrl =
    `${PROJECT_ENDPOINT}/toolboxes/${toolbox.name}` +
    `/versions/${toolbox.version}/mcp?api-version=v1`;

  // 3. Create a remote-tool project connection that points at the toolbox endpoint.
  //    Use a user Entra token so the caller's identity is passed through
  //    (audience https://ai.azure.com). Create the connection once, for example
  //    with the Azure Developer CLI:
  //
  //    azd ai connection create mcp-server-toolbox-conn \
  //      --kind remote-tool \
  //      --target "<toolboxMcpUrl>" \
  //      --auth-type user-entra-token \
  //      --audience https://ai.azure.com
  const toolboxConnectionName = "mcp-server-toolbox-conn";

  // 4. Attach the toolbox to a prompt agent as an MCP tool.
  const agent = await project.agents.createVersion("agent-mcp-connection-auth", {
    kind: "prompt",
    model: "gpt-5-mini",
    instructions: "Use MCP tools as needed",
    tools: [
      {
        type: "mcp",
        server_label: "toolbox",
        server_url: toolboxMcpUrl,
        require_approval: "always",
        project_connection_id: toolboxConnectionName,
      },
    ],
  });
  console.log(`Agent created (id: ${agent.id}, name: ${agent.name}, version: ${agent.version})`);

  // Create a conversation thread to maintain context across multiple interactions
  console.log("\nCreating conversation...");
  const conversation = await openai.conversations.create();
  console.log(`Created conversation (id: ${conversation.id})`);

  // Send initial request that will trigger the MCP tool
  console.log("\nSending request that will trigger MCP approval...");
  const response = await openai.responses.create(
    {
      conversation: conversation.id,
      input: "What is my username in my GitHub profile?",
    },
    {
      body: { agent_reference: { name: agent.name, type: "agent_reference" } },
    },
  );

  // Process any MCP approval requests that were generated
  const inputList: OpenAI.Responses.ResponseInputItem.McpApprovalResponse[] = [];

  const rl = readline.createInterface({ input: process.stdin, output: process.stdout });
  const ask = (q: string) => new Promise<string>((resolve) => rl.question(q, resolve));
  for (const item of response.output) {
    if (item.type === "mcp_approval_request") {
      if (item.server_label === "toolbox" && item.id) {
        console.log(`\nReceived MCP approval request (id: ${item.id})`);
        console.log(`  Server: ${item.server_label}`);
        console.log(`  Tool: ${item.name}`);

        // Approve only after you review the tool call.
        // In production, implement your own approval UX and policy.
        const answer = (await ask("Approve this MCP tool call? (y/N): ")).trim().toLowerCase();
        const approve = answer === "y";
        inputList.push({
          type: "mcp_approval_response",
          approval_request_id: item.id,
          approve,
        });
      }
    }
  }

  rl.close();

  console.log(`\nProcessing ${inputList.length} approval request(s)`);
  console.log("Final input:");
  console.log(JSON.stringify(inputList, null, 2));

  // Send the approval response back to continue the agent's work
  // This allows the MCP tool to access the GitHub repository and complete the original request
  console.log("\nSending approval response...");
  const finalResponse = await openai.responses.create(
    {
      input: inputList,
      previous_response_id: response.id,
    },
    {
      body: { agent_reference: { name: agent.name, type: "agent_reference" } },
    },
  );

  console.log(`\nResponse: ${finalResponse.output_text}`);

  // Clean up resources by deleting the agent version and conversation
  // This prevents accumulation of unused resources in your project
  console.log("\nCleaning up resources...");
  await openai.conversations.delete(conversation.id);
  console.log("Conversation deleted");

  await project.agents.deleteVersion(agent.name, agent.version);
  console.log("Agent deleted");

  console.log("\nMCP with project connection sample completed!");
}

main().catch((err) => {
  console.error("The sample encountered an error:", err);
});

預期產出

以下範例顯示執行樣本時的預期輸出:

Creating agent with MCP tool using project connection...
Agent created (id: <agent-id>, name: agent-mcp-connection-auth, version: 1)
Creating conversation...
Created conversation (id: <conversation-id>)
Sending request that will trigger MCP approval...
Received MCP approval request (id: <approval-request-id>)
  Server: toolbox
  Tool: get-github-username
Processing 1 approval request(s)
Final input:
[
  {
    "type": "mcp_approval_response",
    "approval_request_id": "<approval-request-id>",
    "approve": true
  }
]
Sending approval response...
Response: Your GitHub username is "example-username".
Cleaning up resources...
Conversation deleted
Agent deleted
MCP with project connection sample completed!

在 Java 代理中使用 MCP 工具

提示

大多數經紀人會使用 工具箱 來新增檔案搜尋工具,並將工具箱附加到您的經紀人身上作為 MCP 工具。 *如果你正在使用 Java SDK,目前還沒有建立工具箱的 API。 你可以用 Python、REST API、C#、TypeScript 或 Foundry 入口網站建立工具箱,然後從你的 Java 代理中引用它的 MCP 端點作為 McpTool.

新增相依性至您的pom.xml:

<dependency>
    <groupId>com.azure</groupId>
    <artifactId>azure-ai-agents</artifactId>
    <version>2.2.0</version>
</dependency>

使用 MCP 工具建立代理人

import com.azure.ai.agents.AgentsClient;
import com.azure.ai.agents.AgentsClientBuilder;
import com.azure.ai.agents.ResponsesClient;
import com.azure.ai.agents.models.AgentReference;
import com.azure.ai.agents.models.AgentVersionDetails;
import com.azure.ai.agents.models.AzureCreateResponseOptions;
import com.azure.ai.agents.models.McpTool;
import com.azure.ai.agents.models.PromptAgentDefinition;
import com.azure.identity.DefaultAzureCredentialBuilder;
import com.openai.models.responses.Response;
import com.openai.models.responses.ResponseCreateParams;

import java.util.Collections;

public class McpToolExample {
    public static void main(String[] args) {
        // Format: "https://resource_name.ai.azure.com/api/projects/project_name"
        String projectEndpoint = "your_project_endpoint";
        // Create the toolbox out-of-band by using Python, REST, the Foundry portal, C#, or TypeScript.
        String toolboxMcpUrl = projectEndpoint + "/toolboxes/mcp-server-toolbox/versions/1/mcp?api-version=v1";
        String toolboxConnectionName = "mcp-server-toolbox-conn";

        AgentsClientBuilder builder = new AgentsClientBuilder()
            .credential(new DefaultAzureCredentialBuilder().build())
            .endpoint(projectEndpoint);

        AgentsClient agentsClient = builder.buildAgentsClient();
        ResponsesClient responsesClient = builder.buildResponsesClient();

        // Attach the toolbox MCP endpoint with server label, URL, connection, and approval mode.
        McpTool mcpTool = new McpTool("toolbox")
            .setServerUrl(toolboxMcpUrl)
            .setProjectConnectionId(toolboxConnectionName)
            .setRequireApproval("always");

        // Create agent with MCP tool
        PromptAgentDefinition agentDefinition = new PromptAgentDefinition("gpt-5-mini")
            .setInstructions("You are a helpful assistant that can use MCP tools.")
            .setTools(Collections.singletonList(mcpTool));

        AgentVersionDetails agent = agentsClient.createAgentVersion("mcp-agent", agentDefinition);
        System.out.printf("Agent created: %s (version %s)%n", agent.getName(), agent.getVersion());

        // Create a response
        AgentReference agentReference = new AgentReference(agent.getName())
            .setVersion(agent.getVersion());

        Response response = responsesClient.createAzureResponse(
            new AzureCreateResponseOptions().setAgentReference(agentReference),
            ResponseCreateParams.builder()
                .input("Summarize the Azure REST API specifications"));

        System.out.println("Response: " + response.output());

        // Clean up
        agentsClient.deleteAgentVersion(agent.getName(), agent.getVersion());
    }
}

預期產出

Agent created: mcp-agent (version 1)
Response: [ResponseOutputItem containing MCP tool results ...]

使用 MCP 工具搭配 REST API

以下範例展示了如何使用 MCP 工具建立代理,並透過回應 API 呼叫。 如果回應包含一個設定 type 為 mcp_approval_request的輸出項目,則會發送包含該 mcp_approval_response 項目的後續請求。

先決條件

設定以下環境變數:

  • FOUNDRY_PROJECT_ENDPOINT: 你的專案端點網址。
  • FOUNDRY_MODEL_DEPLOYMENT_NAME:你的模型部署名稱。
  • AGENT_TOKEN:Foundry 的持有人權杖。
  • MCP_PROJECT_CONNECTION_NAME (可選):你的 MCP 專案連結名稱。

取得存取權憑證:

export AGENT_TOKEN=$(az account get-access-token --scope "https://ai.azure.com/.default" --query accessToken -o tsv)

如果工具箱內的 MCP 伺服器不需要認證,就在 project_connection_id 工具箱工具定義中省略。 代理的 MCP 工具仍用於 project_connection_id 遠端工具與工具箱端點的連接。

註

對於 REST API,請使用您為工具組端點建立的遠端工具專案連線名稱,作為代理程式 MCP 工具上的project_connection_id。

提示

關於 MCP 工具架構與核准項目的詳細資訊,請參閱 Microsoft Foundry REST API 參考文獻。

1. 使用 MCP 伺服器建立工具箱

建議新增 MCP 伺服器的方法是透過工具箱,然後將工具箱綁定為你的代理程式作為 MCP 工具。 請參考 什麼是工具箱?

curl -X POST "$FOUNDRY_PROJECT_ENDPOINT/toolboxes/mcp-server-toolbox/versions?api-version=v1" \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $AGENT_TOKEN" \
  -d '{
    "description": "Toolbox with the Azure REST API specifications MCP server",
    "tools": [
      {
        "type": "mcp",
        "server_label": "api-specs",
        "server_url": "https://gitmcp.io/Azure/azure-rest-api-specs",
        "require_approval": "never"
      }
    ]
  }'

工具箱在 處暴露一個與 MCP 相容的端點 $FOUNDRY_PROJECT_ENDPOINT/toolboxes/mcp-server-toolbox/versions/<version>/mcp?api-version=v1,其中 <version> 是前一次呼叫回傳的版本。

2. 建立與工具箱的遠端工具連線

建立一個遠端工具專案連線,指向工具箱端點。 使用使用者 Entra 權杖,以便呼叫者的身分識別得以傳遞 (對象https://ai.azure.com):

azd ai connection create mcp-server-toolbox-conn \
  --kind remote-tool \
  --target "$FOUNDRY_PROJECT_ENDPOINT/toolboxes/mcp-server-toolbox/versions/<version>/mcp?api-version=v1" \
  --auth-type user-entra-token \
  --audience https://ai.azure.com

3. 建立 MCP 代理

curl -X POST "$FOUNDRY_PROJECT_ENDPOINT/agents?api-version=v1" \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $AGENT_TOKEN" \
  -d '{
    "name": "<AGENT_NAME>-mcp",
    "description": "MCP agent",
    "definition": {
      "kind": "prompt",
      "model": "'$FOUNDRY_MODEL_DEPLOYMENT_NAME'",
      "instructions": "You are a helpful agent that can use MCP tools to assist users. Use the available MCP tools to answer questions and perform tasks.",
      "tools": [
        {
          "type": "mcp",
          "server_label": "toolbox",
          "server_url": "'$FOUNDRY_PROJECT_ENDPOINT'/toolboxes/mcp-server-toolbox/versions/<version>/mcp?api-version=v1",
          "require_approval": "always",
          "project_connection_id": "mcp-server-toolbox-conn"
        }
      ]
    }
  }'

若要在工具箱內使用認證的 MCP 伺服器,請在工具箱工具定義中新增 "project_connection_id": "'$MCP_PROJECT_CONNECTION_NAME'" 資料。 變更 server_url 至已認證的伺服器端點(例如, https://api.githubcopilot.com/mcp)。

4. 建立回應

curl -X POST "$FOUNDRY_PROJECT_ENDPOINT/openai/v1/responses" \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $AGENT_TOKEN" \
  -d '{
    "agent": {"type": "agent_reference", "name": "<AGENT_NAME>-mcp"},
    "input": "Please summarize the Azure REST API specifications Readme"
  }'

如果回應包含一個設定 type 為 mcp_approval_request的輸出項目,則將批准請求項目 id 複製為 APPROVAL_REQUEST_ID。 同時將頂層回應 id 複製為 PREVIOUS_RESPONSE_ID。

5. 發送批准回覆

若 MCP 工具需要核准,請發送後續請求:

curl -X POST "$FOUNDRY_PROJECT_ENDPOINT/openai/v1/responses" \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $AGENT_TOKEN" \
  -d '{
    "previous_response_id": "'$PREVIOUS_RESPONSE_ID'",
    "input": [
      {
        "type": "mcp_approval_response",
        "approval_request_id": "'$APPROVAL_REQUEST_ID'",
        "approve": true
      }
    ]
  }'

6.清除資源

刪除代理人:

curl -X DELETE "$FOUNDRY_PROJECT_ENDPOINT/agents/<AGENT_NAME>-mcp?api-version=v1" \
  -H "Authorization: Bearer $AGENT_TOKEN"

運作原理

你需要將遠端 MCP 伺服器(現有的 MCP 伺服器端點)帶到 Foundry Agent Service。 您可以將多個遠端 MCP 伺服器作為工具加入。 每個工具都需要在同一代理內提供一個唯一的 server_label 值,以及一個與遠端 MCP 伺服器關聯的 server_url 值。 務必仔細檢視你新增到 Foundry 代理服務的 MCP 伺服器。

除了透過 URL 連接任意遠端 MCP 伺服器外,你也可以直接從 Foundry 新增工具 目錄新增一些 MCP 伺服器。 例如,Azure DevOps MCP Server 可作為目錄項目提供。 Azure DevOps 會架設遠端 MCP 端點,並透過可串流的 HTTP 公開,所以你從 Foundry 目錄新增伺服器時,不需要安裝或托管伺服器。 目錄條目簡化了連線設定,並與本文所述的審核與稽核機制保持一致。

欲了解更多使用 MCP 的資訊,請參見:

設定 MCP 連線

次要路線 - 進階作戰: 在首次成功路徑後使用此參考,限制工具、變更審核行為或新增專案連結。

以下步驟說明如何從 Foundry Agent Service 連接遠端 MCP 伺服器:

  1. 找到你想連接的遠端 MCP 伺服器,例如 GitHub MCP 伺服器。 使用以下資訊來建立或更新配有 mcp 工具的 Foundry 代理。
    1. server_url: MCP 伺服器的網址,例如 https://api.githubcopilot.com/mcp/。
    2. server_label: 是該 MCP 伺服器對代理者的唯一識別碼,例如 github。
    3. allowed_tools:一份可選的工具清單,供該代理人存取與使用。 如果你沒有提供這個值,預設值會包含 MCP 伺服器中的所有工具。
    4. require_approval:可選擇性地決定是否需要核准。 預設值為 always。 支援的值有:
      • always開發商需要為每通電話提供批准。 如果你沒有提供一個數值,這個就是預設值。
      • never:不需要批准。
      • {"never":[<tool_name_1>, <tool_name_2>]}你提供一份不需要核准的工具清單。
      • {"always":[<tool_name_1>, <tool_name_2>]}你提供了需要核准的工具清單。
  2. project_connection_id: 專案連線 ID,儲存 MCP 伺服器的認證及其他連線細節。
  3. 如果模型嘗試在你的 MCP 伺服器中呼叫工具並需經過核准,你會得到一個回應輸出項目類型為 mcp_approval_request。 在回應輸出項目中,你可以獲得更多關於 MCP 伺服器中哪個工具被呼叫及要傳遞參數的詳細資訊。 檢視工具與論點,以便做出明智的批准決定。
  4. 請使用 previous_response_id 並將 設定 approve 為 true,向代理人提交核准。

連接到 Azure DevOps MCP 伺服器

Azure DevOps MCP Server 可作為 Foundry 的目錄項目取得。

Important

遠端 Azure DevOps MCP 伺服器使用 Microsoft Entra ID 進行認證。 你的 Azure DevOps 組織必須有 Microsoft Entra 租戶作為後盾。 獨立的 Microsoft 帳戶(MSA)組織不被支援。

若要新增伺服器:

  1. 在 Foundry 入口網站中,前往您的專案。
  2. 選擇 Add Tools>Catalog並搜尋「Azure DevOps」。
  3. 選擇 Azure DevOps MCP Server,然後選擇 Create.
  4. 輸入您的Azure DevOps組織名稱,並選擇Connect。
  5. 選擇要暴露給代理的 Azure DevOps 工具。 你可以選擇一部分工具來精確控制代理人能存取的內容。

這種基於目錄的架構創造了 MCP 工具,供代理使用而無需更改程式碼。 你可以在 Foundry 聊天測試體驗中驗證連接性與工具行為,然後再將工具整合進生產程式碼。

提示

工具箱版本控制:Foundry 工具箱支援版本控制,因此你可以在不影響生產代理的情況下迭代新版本。 針對生產代理程式使用取用者端點 ({project_endpoint}/toolboxes/{name}/mcp?api-version=v1),此端點一律提供已升級的預設版本。 使用版本專屬端點{project_endpoint}/toolboxes/{name}/versions/{version}/mcp?api-version=v1()進行測試,再進行推廣。 即使切換 Toolbox 版本,也要保持 server_label 每個代理人的獨特性。 詳情請參見 「升級版本為預設」。

長時間執行作業 (預覽版)

次要路徑 - 背景模式: 只有當 MCP 操作無法在標準同步逾時內完成時,才使用此模式。

部分 MCP 伺服器會提供一些工具,而這些工具需要超過標準同步逾時時間才會回傳結果。 為了支援這些操作,請將代理程式置 於背景模式。 背景模式會非同步執行回應,因此 MCP 工具呼叫可以繼續且不需保持連線開啟,並輪詢回應狀態直到完成。 此方法讓 MCP 工具呼叫超過 Known Limitations 中描述的 100 秒非串流逾時。

註

長時間執行 MCP 作業目前為預覽版。 預覽功能是在沒有服務等級合約的情況下提供的,不建議用於生產工作負載。 行為和支持的模型是可以改變的。

MCP 伺服器的需求

代理執行時依賴 MCP 伺服器非同步執行操作並回報進度。 伺服器必須:

  • 實作 模型情境協定(Model Context Protocol)任務功能 ,讓工具呼叫能回傳任務參考,而非阻塞直到工作完成。
  • 啟動長時間執行作業時,在工具結果中繼資料中傳回相關工作識別碼 (io.modelcontextprotocol/related-task 欄位,搭配 taskId)。
  • 提供一種機制,讓執行階段輪詢任務狀態,並在任務完成後取得最終結果。
  • 作為遠端 MCP 端點可存取,與其他 MCP 工具相同。 本地 MCP 伺服器必須自架,才能提供遠端端點。 請參見 「Host a local MCP server」。

當代理程式執行階段呼叫會啟動長時間執行作業的工具時,伺服器會回傳任務參照,而執行階段則會在背景中保留該回應。 執行階段會啟動回應,立即傳回包含回應 id 以及 status 為 queued 的回應,並在工作完成時收集結果。 你輪詢回應 id 直到 status 變成 completed,然後讀取最終輸出。

用於長時間執行的 MCP 操作的背景模式適用於任何支援背景模式的模型,例如 gpt-5.4 或 gpt-5.5。

如果你的代理使用不支援背景模式的模型,MCP 工具呼叫會同步執行,並受到 100 秒逾時的影響。

在 Microsoft Foundry 入口網站啟用背景模式

你可以在 Microsoft Foundry 入口網站遊樂場開啟代理程式的背景模式,無需撰寫程式碼:

  1. 打開你的代理人,選擇 Playground 標籤。

  2. 在 模型 清單中,選擇支援背景模式的模型,例如 gpt-5.4 或 gpt-5.5。

  3. 選擇模型旁的參數圖示,開啟 背景模式。

  4. 在工具中,新增一個支援 MCP 任務的 MCP 伺服器工具,例如透過 Fabric IQ 工具新增的 Fabric 資料代理程式。 相關步驟請參見「用 Fabric IQ 連接代理程式至 Microsoft Fabric」。

  5. 傳達訊息。 Agent 會啟動背景工作執行,並在長時間執行的工具呼叫完成期間顯示其進度。 當執行結束後,回應會顯示在聊天中。

用程式碼執行背景模式

以下範例會叫用已設定好 MCP 工具的代理、將 background 設為 true,並持續輪詢直到回應完成。 將佔位符的值替換為您自己的數值。

from time import sleep
from azure.identity import DefaultAzureCredential
from azure.ai.projects import AIProjectClient

PROJECT_ENDPOINT = "your_project_endpoint"
AGENT_NAME = "your_mcp_agent_name"

project = AIProjectClient(
    endpoint=PROJECT_ENDPOINT,
    credential=DefaultAzureCredential(),
)
openai = project.get_openai_client()

# Start a background response. It returns immediately with status "queued".
response = openai.responses.create(
    extra_body={
        "agent_reference": {
            "name": AGENT_NAME,
            "type": "agent_reference",
        }
    },
    input="Run the long-running task and summarize the result.",
    background=True,
)

# Poll the response ID until the MCP tool call completes.
while response.status in ("queued", "in_progress"):
    sleep(5)
    response = openai.responses.retrieve(response.id)

print(response.output_text)
using Azure.Identity;
using Azure.AI.Projects;

var projectEndpoint = "your_project_endpoint";
var agentName = "your_mcp_agent_name";

AIProjectClient projectClient = new(
    endpoint: new Uri(projectEndpoint),
    tokenProvider: new DefaultAzureCredential());

ProjectResponsesClient responsesClient
    = projectClient.ProjectOpenAIClient.GetProjectResponsesClientForAgent(agentName);

// Start a background response. It returns immediately with status "queued".
ResponseResult response = await responsesClient.CreateResponseAsync(
    new CreateResponseOptions
    {
        InputItems = { ResponseItem.CreateUserMessageItem(
            "Run the long-running task and summarize the result.") },
        Background = true,
    });

// Poll the response ID until the MCP tool call completes.
while (response.Status is "queued" or "in_progress")
{
    await Task.Delay(5000);
    response = await responsesClient.RetrieveResponseAsync(response.Id);
}
Console.WriteLine(response.GetOutputText());
import { DefaultAzureCredential } from "@azure/identity";
import { AIProjectClient } from "@azure/ai-projects";

const PROJECT_ENDPOINT = "your_project_endpoint";
const AGENT_NAME = "your_mcp_agent_name";

const project = new AIProjectClient(PROJECT_ENDPOINT, new DefaultAzureCredential());
const openai = project.getOpenAIClient();

// Start a background response. It returns immediately with status "queued".
let response = await openai.responses.create(
  {
    input: "Run the long-running task and summarize the result.",
    background: true,
  },
  { body: { agent_reference: { name: AGENT_NAME, type: "agent_reference" } } },
);

// Poll the response ID until the MCP tool call completes.
while (response.status === "queued" || response.status === "in_progress") {
  await new Promise((r) => setTimeout(r, 5000));
  response = await openai.responses.retrieve(response.id);
}
console.log(response.output_text);
import com.azure.ai.agents.*;
import com.azure.ai.agents.models.AgentReference;
import com.azure.ai.agents.models.AzureCreateResponseOptions;
import com.azure.identity.DefaultAzureCredentialBuilder;
import com.openai.models.responses.Response;
import com.openai.models.responses.ResponseCreateParams;

String projectEndpoint = "your_project_endpoint";
String agentName = "your_mcp_agent_name";

AgentsClientBuilder builder = new AgentsClientBuilder()
    .credential(new DefaultAzureCredentialBuilder().build())
    .endpoint(projectEndpoint);
ResponsesClient responsesClient = builder.buildResponsesClient();

AgentReference agentRef = new AgentReference(agentName);

// Start a background response. It returns immediately with status "queued".
Response response = responsesClient.createAzureResponse(
    new AzureCreateResponseOptions()
        .setAgentReference(agentRef)
        .setBackground(true),
    ResponseCreateParams.builder()
        .input("Run the long-running task and summarize the result."));

// Poll the response ID until the MCP tool call completes.
while (response.status().equals("queued") || response.status().equals("in_progress")) {
    Thread.sleep(5000);
    response = responsesClient.getAzureResponse(response.id());
}
System.out.println(response.output());

建立背景回應。 要求會立即傳回包含回應 id 以及 status 為 queued 的回應:

curl -X POST "$FOUNDRY_PROJECT_ENDPOINT/openai/v1/responses" \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $AGENT_TOKEN" \
  -d '{
    "agent": {"type": "agent_reference", "name": "<AGENT_NAME>-mcp"},
    "input": "Run the long-running task and summarize the result.",
    "background": true
  }'

從結果中複製回應 id,然後輪詢該回應,直到 status 為 completed:

curl "$FOUNDRY_PROJECT_ENDPOINT/openai/v1/responses/$RESPONSE_ID" \
  -H "Authorization: Bearer $AGENT_TOKEN"

當 status 為 completed 時,output 陣列包含 MCP 工具呼叫結果及最終的助理訊息。

已知限制

次要路徑 - 串流行為: 如果您的用戶端串流回應或您的 MCP 呼叫接近同步逾時,請在第一個成功路由之後檢閱這些限制。

  • 非串流 MCP 工具呼叫逾時:非串流 MCP 工具呼叫有 100 秒的逾時。 如果你的 MCP 伺服器回應超過 100 秒,通話就會失敗。 為避免逾時,請確保您的 MCP 伺服器在此範圍內回應。 如果你的使用情境需要更長的處理時間,可以在 背景模式 中運行代理並使用支援的模型,優化伺服器端邏輯,或將操作拆分成更小的步驟。
  • 私有 MCP 需要標準代理設定:私有 MCP 伺服器連接僅能透過 標準代理設定搭配私有網路 (BYO VNet)提供。 基本代理設定不支援私有 MCP 端點。
  • Private MCP hosting:專用 MCP 子網路上的Azure 容器應用程式是私有 MCP 伺服器的測試配置。 功能應用或應用服務作為私有 MCP 伺服器主機可能可行,但內部驗證不佳。

常見問題與錯誤

當你使用 MCP 工具搭配 Foundry Agent Service 時,可能會發生以下常見問題:

  • 「工具架構無效」:

    此錯誤通常發生在 MCP 伺服器定義包含 anyOf 或 allOf,或參數接受多種值時。 更新你的 MCP 伺服器定義,再試一次。

  • MCP 伺服器回傳的「未授權」或「禁止」狀態:

    確認 MCP 伺服器支援你的認證方式,並驗證專案連線中儲存的憑證。 對於 GitHub,使用最低權限的代幣並定期輪換。 對於 Azure DevOps MCP Server,請確認組織是否有 Microsoft Entra 租戶支援,並且你能在 Foundry 中完成組織連線流程。 獨立的 Microsoft 帳戶 組織不被支援。

  • 模型從不呼叫你的 MCP 工具:

    請確認您的代理程式指示鼓勵使用工具,並驗證 server_label、server_url 和 allowed_tools 值。 如果你設定 allowed_tools了 ,請確保工具名稱與 MCP 伺服器所暴露的名稱相符。

  • 代理程式在核准後從未繼續執行:

    確認你發送了後續請求,並 previous_response_id 設定為原始回應 ID,並且你使用核准請求項目 ID 為 approval_request_id。

架設本地 MCP 伺服器

代理服務執行時僅接受遠端 MCP 伺服器端點。 如果你想從本地 MCP 伺服器新增工具,你需要在 Azure 容器應用程式 或 Azure Functions 自行架設,才能取得遠端 MCP 伺服器端點。

遠端端點可以是 VNet 內的公開端點或私有端點。 對於私人 MCP 伺服器,請在專用的 MCP 子網部署具有內部專用入口的容器化應用程式--internal-only true。 請參閱 公用與私有 MCP 伺服器端 點以了解設定細節。

在雲端架設本地 MCP 伺服器時,請考慮以下因素:

本地 MCP 伺服器設定 在 Azure 容器應用中託管 在 Azure Functions 上託管
交通 需要 HTTP POST/GET 端點。 需要具備 HTTP 串流能力。
法規變更 需要重新組裝貨櫃。 Azure Functions專用配置檔必須在根目錄中。
認證 需要自訂認證實作。 僅限金鑰型。 OAuth 需要 API 管理。
語言 任何能在 Linux 容器中運行的語言(Python、Node.js、.NET、TypeScript、Go)。 Python、Node.js、Java、.NET。
容器需求 只用 Linux(linux/amd64)。 沒有特權容器。 容器化伺服器不被支援。
相依關係 所有相依關係必須在容器映像中。 作業系統層級的依賴項(例如 Playwright)不受支援。
州 僅限無國籍者。 僅限無國籍者。
UVX/NPX 有支援。 不支援。 npx 不支援啟動指令。