404 lines
17 KiB
Plaintext
404 lines
17 KiB
Plaintext
{
|
|
"cells": [
|
|
{
|
|
"cell_type": "markdown",
|
|
"id": "b8c57858",
|
|
"metadata": {},
|
|
"source": [
|
|
"# Azure AI-Agents mit Unterstützung für das Model Context Protocol (MCP) - Python\n",
|
|
"\n",
|
|
"Dieses Notebook zeigt, wie Azure AI-Agents mit den Model Context Protocol (MCP)-Tools in Python verwendet werden können. Es wird demonstriert, wie ein intelligenter Agent erstellt werden kann, der externe MCP-Server (wie Microsoft Learn) für erweiterte Funktionen mithilfe einer schlüssellosen Authentifizierung nutzen kann.\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"id": "2e6e4234",
|
|
"metadata": {},
|
|
"source": [
|
|
"## Erforderliche Python-Pakete installieren\n",
|
|
"\n",
|
|
"Zuerst müssen wir die notwendigen Python-Pakete installieren:\n",
|
|
"- **azure-ai-projects**: Kern-SDK für Azure AI Projects\n",
|
|
"- **azure-ai-agents**: Azure AI Agents SDK zum Erstellen und Verwalten von Agents\n",
|
|
"- **azure-identity**: Ermöglicht schlüssellose Authentifizierung mit DefaultAzureCredential\n",
|
|
"- **mcp**: Implementierung des Model Context Protocols für Python\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"id": "6a2e9a05",
|
|
"metadata": {},
|
|
"source": [
|
|
"## Vorteile der schlüssellosen Authentifizierung\n",
|
|
"\n",
|
|
"Dieses Notebook demonstriert die **schlüssellose Authentifizierung**, die mehrere Vorteile bietet:\n",
|
|
"- ✅ **Keine API-Schlüssel zu verwalten** - Verwendet Azure-Identitätsbasierte Authentifizierung\n",
|
|
"- ✅ **Erhöhte Sicherheit** - Keine Geheimnisse im Code oder in Konfigurationsdateien gespeichert\n",
|
|
"- ✅ **Automatische Anmeldeinformationen-Rotation** - Azure übernimmt das Lebenszyklusmanagement der Anmeldeinformationen\n",
|
|
"- ✅ **Rollenbasierte Zugriffskontrolle** - Nutzt Azure RBAC für fein abgestufte Berechtigungen\n",
|
|
"- ✅ **Unterstützung für mehrere Umgebungen** - Funktioniert nahtlos in Entwicklungs- und Produktionsumgebungen\n",
|
|
"\n",
|
|
"Die `DefaultAzureCredential` wählt automatisch die beste verfügbare Anmeldeinformationsquelle aus:\n",
|
|
"1. **Managed Identity** (bei Ausführung in Azure)\n",
|
|
"2. **Azure CLI**-Anmeldeinformationen (während der lokalen Entwicklung)\n",
|
|
"3. **Visual Studio**-Anmeldeinformationen\n",
|
|
"4. **Umgebungsvariablen** (falls konfiguriert)\n",
|
|
"5. **Interaktive Browser**-Authentifizierung (als Rückfalloption)\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"id": "43efa94d",
|
|
"metadata": {},
|
|
"source": [
|
|
"## Einrichtung der schlüssellosen Authentifizierung\n",
|
|
"\n",
|
|
"**Voraussetzungen für die schlüssellose Authentifizierung:**\n",
|
|
"\n",
|
|
"### Für lokale Entwicklung:\n",
|
|
"```bash\n",
|
|
"# Install Azure CLI and login\n",
|
|
"az login\n",
|
|
"# Verify your identity\n",
|
|
"az account show\n",
|
|
"```\n",
|
|
"\n",
|
|
"### Für Azure-Umgebungen:\n",
|
|
"- Aktivieren Sie die **Systemzugewiesene Verwaltete Identität** auf Ihrer Azure-Ressource\n",
|
|
"- Weisen Sie der verwalteten Identität die entsprechenden **RBAC-Rollen** zu:\n",
|
|
" - `Cognitive Services OpenAI User` für den Zugriff auf Azure OpenAI\n",
|
|
" - `AI Developer` für den Zugriff auf Azure AI-Projekte\n",
|
|
"\n",
|
|
"### Umgebungsvariablen (Optional):\n",
|
|
"```python\n",
|
|
"# These are automatically detected by DefaultAzureCredential\n",
|
|
"# AZURE_CLIENT_ID=<your-client-id>\n",
|
|
"# AZURE_CLIENT_SECRET=<your-client-secret>\n",
|
|
"# AZURE_TENANT_ID=<your-tenant-id>\n",
|
|
"```\n",
|
|
"\n",
|
|
"**Keine API-Schlüssel oder Verbindungszeichenfolgen erforderlich!** 🔐\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"id": "2e21387d",
|
|
"metadata": {},
|
|
"outputs": [],
|
|
"source": [
|
|
"! pip install azure-ai-projects -U\n",
|
|
"! pip install azure-ai-agents==1.1.0b4 -U\n",
|
|
"! pip install azure-identity -U\n",
|
|
"! pip install mcp==1.11.0 -U"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"id": "b31c8873",
|
|
"metadata": {},
|
|
"source": [
|
|
"## Erforderliche Bibliotheken importieren\n",
|
|
"\n",
|
|
"Importieren Sie die notwendigen Python-Module:\n",
|
|
"- **os, time**: Standard-Python-Bibliotheken für Umgebungsvariablen und Verzögerungen\n",
|
|
"- **AIProjectClient**: Hauptclient für Azure AI-Projekte\n",
|
|
"- **DefaultAzureCredential**: Schlüssellose Authentifizierung für Azure-Dienste\n",
|
|
"- **MCP-bezogene Klassen**: Zum Erstellen und Verwalten von MCP-Tools und Bearbeiten von Genehmigungen\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"id": "43667b32",
|
|
"metadata": {},
|
|
"outputs": [],
|
|
"source": [
|
|
"import os, time\n",
|
|
"from azure.ai.projects import AIProjectClient\n",
|
|
"from azure.identity import DefaultAzureCredential\n",
|
|
"from azure.ai.agents.models import McpTool, RequiredMcpToolCall, SubmitToolApprovalAction, ToolApproval\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"id": "721355e5",
|
|
"metadata": {},
|
|
"source": [
|
|
"## Konfigurieren der MCP-Server-Einstellungen\n",
|
|
"\n",
|
|
"Richten Sie die MCP-Server-Konfiguration mithilfe von Umgebungsvariablen mit Standardwerten als Fallback ein:\n",
|
|
"- **MCP_SERVER_URL**: Die URL des MCP-Servers (standardmäßig Microsoft Learn API)\n",
|
|
"- **MCP_SERVER_LABEL**: Eine Bezeichnung zur Identifizierung des MCP-Servers (standardmäßig \"mslearn\")\n",
|
|
"\n",
|
|
"Dieser Ansatz ermöglicht eine flexible Konfiguration in verschiedenen Umgebungen.\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"id": "189f3d55",
|
|
"metadata": {},
|
|
"outputs": [],
|
|
"source": [
|
|
"mcp_server_url = os.environ.get(\"MCP_SERVER_URL\", \"https://learn.microsoft.com/api/mcp\")\n",
|
|
"mcp_server_label = os.environ.get(\"MCP_SERVER_LABEL\", \"mslearn\")"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"id": "20612d9a",
|
|
"metadata": {},
|
|
"source": [
|
|
"## Erstellen eines Azure AI Project Clients (Schlüssellose Authentifizierung)\n",
|
|
"\n",
|
|
"Initialisieren Sie den Azure AI Project Client mit **schlüsselloser Authentifizierung**:\n",
|
|
"- **endpoint**: Die URL des Azure AI Foundry Projektendpunkts\n",
|
|
"- **credential**: Verwendet `DefaultAzureCredential()` für eine sichere, schlüssellose Authentifizierung\n",
|
|
"- **Keine API-Schlüssel erforderlich**: Erkennt und verwendet automatisch die beste verfügbare Anmeldeinformation\n",
|
|
"\n",
|
|
"**Authentifizierungsablauf:**\n",
|
|
"1. Überprüft die Managed Identity (in Azure-Umgebungen)\n",
|
|
"2. Greift auf Azure CLI-Anmeldeinformationen zurück (für lokale Entwicklung)\n",
|
|
"3. Nutzt bei Bedarf andere verfügbare Anmeldequellen\n",
|
|
"\n",
|
|
"Dieser Ansatz eliminiert die Notwendigkeit, API-Schlüssel oder Verbindungszeichenfolgen in Ihrem Code zu verwalten.\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"id": "36b1dbd8",
|
|
"metadata": {},
|
|
"outputs": [],
|
|
"source": [
|
|
"project_client = AIProjectClient(\n",
|
|
" endpoint=\"Your Azure AI Foundry Endpoint\",\n",
|
|
" credential=DefaultAzureCredential(),\n",
|
|
")"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"id": "cdb6ab8c",
|
|
"metadata": {},
|
|
"source": [
|
|
"## Erstellen einer MCP-Tool-Definition\n",
|
|
"\n",
|
|
"Erstellen Sie ein MCP-Tool, das eine Verbindung zum Microsoft Learn MCP-Server herstellt:\n",
|
|
"- **server_label**: Bezeichner für den MCP-Server\n",
|
|
"- **server_url**: URL-Endpunkt des MCP-Servers\n",
|
|
"- **allowed_tools**: Optionale Liste, um einzuschränken, welche Tools verwendet werden können (leere Liste erlaubt alle Tools)\n",
|
|
"\n",
|
|
"Dieses Tool ermöglicht es dem Agenten, auf die Microsoft Learn-Dokumentation und -Ressourcen zuzugreifen.\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"id": "51e7e136",
|
|
"metadata": {},
|
|
"outputs": [],
|
|
"source": [
|
|
"mcp_tool = McpTool(\n",
|
|
" server_label=mcp_server_label,\n",
|
|
" server_url=mcp_server_url,\n",
|
|
" allowed_tools=[], # Optional: specify allowed tools\n",
|
|
")\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"id": "6e894b0b",
|
|
"metadata": {},
|
|
"source": [
|
|
"## Erstellen eines Agenten und Ausführen einer Unterhaltung (Keyless Workflow)\n",
|
|
"\n",
|
|
"Dieser umfassende Abschnitt zeigt den vollständigen **Keyless-Agent-Workflow**:\n",
|
|
"\n",
|
|
"1. **KI-Agent erstellen**: Einen Agenten mit dem GPT-4.1 Nano-Modell und MCP-Tools einrichten\n",
|
|
"2. **Thread erstellen**: Einen Gesprächs-Thread für die Kommunikation einrichten\n",
|
|
"3. **Nachricht senden**: Den Agenten nach den Unterschieden zwischen Azure OpenAI und OpenAI fragen\n",
|
|
"4. **Toolgenehmigungen verwalten**: MCP-Toolaufrufe bei Bedarf automatisch genehmigen\n",
|
|
"5. **Ausführung überwachen**: Den Fortschritt des Agenten verfolgen und erforderliche Aktionen durchführen\n",
|
|
"6. **Ergebnisse anzeigen**: Das Gespräch und die Details zur Toolnutzung anzeigen\n",
|
|
"\n",
|
|
"**Keyless-Funktionen:**\n",
|
|
"- ✅ **Keine fest codierten Geheimnisse** - Alle Authentifizierungen werden über Azure Identity abgewickelt\n",
|
|
"- ✅ **Standardmäßig sicher** - Verwendet rollenbasierte Zugriffskontrolle\n",
|
|
"- ✅ **Vereinfachte Bereitstellung** - Keine Verwaltung von Zugangsdaten erforderlich\n",
|
|
"- ✅ **Audit-freundlich** - Alle Zugriffe werden über Azure Identity nachverfolgt\n",
|
|
"\n",
|
|
"Der Agent wird MCP-Tools verwenden, um auf Microsoft Learn-Ressourcen zuzugreifen, mit voller Sicherheit und ohne API-Schlüsselverwaltung.\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"id": "68c49af5",
|
|
"metadata": {},
|
|
"outputs": [],
|
|
"source": [
|
|
"with project_client:\n",
|
|
" agents_client = project_client.agents\n",
|
|
"\n",
|
|
" # Create a new agent with keyless authentication\n",
|
|
" # NOTE: To reuse existing agent, fetch it with get_agent(agent_id)\n",
|
|
" agent = agents_client.create_agent(\n",
|
|
" model=\"Your Azure OpenAI Model Deployment Name\",\n",
|
|
" name=\"my-mcp-agent\",\n",
|
|
" 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.\",\n",
|
|
" tools=mcp_tool.definitions,\n",
|
|
" )\n",
|
|
" print(f\"Created agent, ID: {agent.id}\")\n",
|
|
" print(f\"MCP Server: {mcp_tool.server_label} at {mcp_tool.server_url}\")\n",
|
|
"\n",
|
|
" # Create thread for communication\n",
|
|
" thread = agents_client.threads.create()\n",
|
|
" print(f\"Created thread, ID: {thread.id}\")\n",
|
|
"\n",
|
|
" # Create message to thread\n",
|
|
" message = agents_client.messages.create(\n",
|
|
" thread_id=thread.id,\n",
|
|
" role=\"user\",\n",
|
|
" content=\"What's difference between Azure OpenAI and OpenAI?\",\n",
|
|
" )\n",
|
|
" print(f\"Created message, ID: {message.id}\")\n",
|
|
"\n",
|
|
" # KEYLESS APPROACH: Handle tool approvals without hardcoded secrets\n",
|
|
" \n",
|
|
" # Option 1: Completely keyless (recommended for Azure identity-enabled MCP servers)\n",
|
|
" # run = agents_client.runs.create(thread_id=thread.id, agent_id=agent.id, tool_resources=mcp_tool.resources)\n",
|
|
" \n",
|
|
" # Option 2: With minimal headers (if MCP server requires specific headers)\n",
|
|
" # For demonstration purposes, using a placeholder header\n",
|
|
" mcp_tool.update_headers(\"SuperSecret\", \"123456\") # Replace with actual auth if needed\n",
|
|
" \n",
|
|
" # Set approval mode - uncomment next line to disable approval requirement completely\n",
|
|
" # mcp_tool.set_approval_mode(\"never\") # Fully automated, no approval needed\n",
|
|
" \n",
|
|
" run = agents_client.runs.create(thread_id=thread.id, agent_id=agent.id, tool_resources=mcp_tool.resources)\n",
|
|
" print(f\"Created run, ID: {run.id}\")\n",
|
|
"\n",
|
|
" while run.status in [\"queued\", \"in_progress\", \"requires_action\"]:\n",
|
|
" time.sleep(1)\n",
|
|
" run = agents_client.runs.get(thread_id=thread.id, run_id=run.id)\n",
|
|
"\n",
|
|
" if run.status == \"requires_action\" and isinstance(run.required_action, SubmitToolApprovalAction):\n",
|
|
" tool_calls = run.required_action.submit_tool_approval.tool_calls\n",
|
|
" if not tool_calls:\n",
|
|
" print(\"No tool calls provided - cancelling run\")\n",
|
|
" agents_client.runs.cancel(thread_id=thread.id, run_id=run.id)\n",
|
|
" break\n",
|
|
"\n",
|
|
" tool_approvals = []\n",
|
|
" for tool_call in tool_calls:\n",
|
|
" if isinstance(tool_call, RequiredMcpToolCall):\n",
|
|
" try:\n",
|
|
" print(f\"Approving tool call: {tool_call}\")\n",
|
|
" \n",
|
|
" # KEYLESS APPROVAL OPTIONS:\n",
|
|
" \n",
|
|
" # Option 1: No headers (fully keyless)\n",
|
|
" # tool_approvals.append(\n",
|
|
" # ToolApproval(\n",
|
|
" # tool_call_id=tool_call.id,\n",
|
|
" # approve=True,\n",
|
|
" # headers={} # No headers needed for keyless\n",
|
|
" # )\n",
|
|
" # )\n",
|
|
" \n",
|
|
" # Option 2: With headers (if MCP server requires them)\n",
|
|
" tool_approvals.append(\n",
|
|
" ToolApproval(\n",
|
|
" tool_call_id=tool_call.id,\n",
|
|
" approve=True,\n",
|
|
" headers=mcp_tool.headers, # Uses configured headers if needed\n",
|
|
" )\n",
|
|
" )\n",
|
|
" except Exception as e:\n",
|
|
" print(f\"Error approving tool_call {tool_call.id}: {e}\")\n",
|
|
"\n",
|
|
" print(f\"tool_approvals: {tool_approvals}\")\n",
|
|
" if tool_approvals:\n",
|
|
" agents_client.runs.submit_tool_outputs(\n",
|
|
" thread_id=thread.id, run_id=run.id, tool_approvals=tool_approvals\n",
|
|
" )\n",
|
|
"\n",
|
|
" print(f\"Current run status: {run.status}\")\n",
|
|
"\n",
|
|
" print(f\"Run completed with status: {run.status}\")\n",
|
|
" if run.status == \"failed\":\n",
|
|
" print(f\"Run failed: {run.last_error}\")\n",
|
|
"\n",
|
|
" # Display run steps and tool calls\n",
|
|
" run_steps = agents_client.run_steps.list(thread_id=thread.id, run_id=run.id)\n",
|
|
"\n",
|
|
" # Loop through each step\n",
|
|
" for step in run_steps:\n",
|
|
" print(f\"Step {step['id']} status: {step['status']}\")\n",
|
|
"\n",
|
|
" # Check if there are tool calls in the step details\n",
|
|
" step_details = step.get(\"step_details\", {})\n",
|
|
" tool_calls = step_details.get(\"tool_calls\", [])\n",
|
|
"\n",
|
|
" if tool_calls:\n",
|
|
" print(\" MCP Tool calls:\")\n",
|
|
" for call in tool_calls:\n",
|
|
" print(f\" Tool Call ID: {call.get('id')}\")\n",
|
|
" print(f\" Type: {call.get('type')}\")\n",
|
|
"\n",
|
|
" print() # add an extra newline between steps\n",
|
|
"\n",
|
|
" # Fetch and log all messages\n",
|
|
" messages = agents_client.messages.list(thread_id=thread.id)\n",
|
|
" print(\"\\nConversation:\")\n",
|
|
" print(\"-\" * 50)\n",
|
|
" for msg in messages:\n",
|
|
" if msg.text_messages:\n",
|
|
" last_text = msg.text_messages[-1]\n",
|
|
" print(f\"{msg.role.upper()}: {last_text.text.value}\")\n",
|
|
" print(\"-\" * 50)\n",
|
|
"\n",
|
|
" # Example of dynamic tool management (keyless)\n",
|
|
" print(f\"\\nDemonstrating keyless dynamic tool management:\")\n",
|
|
" print(f\"Current allowed tools: {mcp_tool.allowed_tools}\")\n",
|
|
" print(\"✅ All operations completed using keyless authentication!\")"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {},
|
|
"source": [
|
|
"\n---\n\n**Haftungsausschluss**: \nDieses Dokument wurde mit dem KI-Übersetzungsdienst [Co-op Translator](https://github.com/Azure/co-op-translator) übersetzt. Obwohl wir uns um Genauigkeit bemühen, beachten Sie bitte, dass automatisierte Übersetzungen Fehler oder Ungenauigkeiten enthalten können. Das Originaldokument in seiner ursprünglichen Sprache sollte als maßgebliche Quelle betrachtet werden. Für kritische Informationen wird eine professionelle menschliche Übersetzung empfohlen. Wir übernehmen keine Haftung für Missverständnisse oder Fehlinterpretationen, die sich aus der Nutzung dieser Übersetzung ergeben.\n"
|
|
]
|
|
}
|
|
],
|
|
"metadata": {
|
|
"kernelspec": {
|
|
"display_name": "demo",
|
|
"language": "python",
|
|
"name": "python3"
|
|
},
|
|
"language_info": {
|
|
"codemirror_mode": {
|
|
"name": "ipython",
|
|
"version": 3
|
|
},
|
|
"file_extension": ".py",
|
|
"mimetype": "text/x-python",
|
|
"name": "python",
|
|
"nbconvert_exporter": "python",
|
|
"pygments_lexer": "ipython3",
|
|
"version": "3.10.15"
|
|
},
|
|
"coopTranslator": {
|
|
"original_hash": "39a035fea0d10767dfcb0662bd3528fa",
|
|
"translation_date": "2025-08-26T21:21:00+00:00",
|
|
"source_file": "05-AdvancedTopics/mcp-foundry-agent-integration/mcp_support_python.ipynb",
|
|
"language_code": "de"
|
|
}
|
|
},
|
|
"nbformat": 4,
|
|
"nbformat_minor": 5
|
|
} |