Teilen über


Integrieren einer App Service-App als MCP-Server für GitHub Copilot Chat (.NET)

In diesem Tutorial erfahren Sie, wie Sie die Funktionen einer ASP.NET Core-App über Model Context Protocol (MCP) verfügbar machen, sie GitHub Copilot als Tool hinzufügen und mit Ihrer App im Agent-Modus des Copilot-Chats interagieren.

Screenshot, der zeigt, wie GitHub Copilot den Todos MCP-Server aufruft, der in Azure App Service gehostet wird.

Wenn Ihre Webanwendung bereits nützliche Funktionen wie Shopping, Hotelbuchung oder Datenverwaltung aufweist, ist es einfach, diese Funktionen verfügbar zu machen für:

Indem Sie Ihrer Web-App einen MCP-Server hinzufügen, können Sie einen Agent aktivieren, um die Funktionen Ihrer App zu verstehen und zu verwenden, wenn er auf Benutzeraufforderungen reagiert. Dies bedeutet, dass ihre App alles tun kann, was der Agent auch tun kann.

  • Fügen Sie Ihrer Web-App einen MCP-Server hinzu.
  • Testen Sie den MCP-Server lokal im GitHub Copilot Chat-Agent-Modus.
  • Stellen Sie den MCP-Server in Azure App Service bereit und stellen Sie eine Verbindung mit dem Server in GitHub Copilot Chat her.

Voraussetzungen

In diesem Lernprogramm wird davon ausgegangen, dass Sie mit dem Beispiel arbeiten, das im Lernprogramm verwendet wird: Bereitstellen einer ASP.NET Core- und Azure SQL-Datenbank-App für Azure App Service.

Öffnen Sie mindestens die Beispielanwendung in GitHub Codespaces, und stellen Sie die App durch Ausführen azd upbereit.

Hinzufügen eines MCP-Servers zu Ihrer Web-App

  1. Fügen Sie im Codespace-Terminal dem Projekt das NuGet-Paket ModelContextProtocol.AspNetCore hinzu:

    dotnet add package ModelContextProtocol.AspNetCore --prerelease
    
  2. Erstellen Sie einen McpServer-Ordner, und erstellen Sie eine TodosMcpTool.cs darin mit dem folgenden Code.

    using DotNetCoreSqlDb.Data;
    using DotNetCoreSqlDb.Models;
    using Microsoft.EntityFrameworkCore;
    using System.ComponentModel;
    using ModelContextProtocol.Server;
    
    namespace DotNetCoreSqlDb.McpServer
    {
        [McpServerToolType]
        public class TodosMcpTool
        {
            private readonly MyDatabaseContext _db;
    
            public TodosMcpTool(MyDatabaseContext db)
            {
                _db = db;
            }
    
            [McpServerTool, Description("Creates a new todo with a description and creation date.")]
            public async Task<string> CreateTodoAsync(
                [Description("Description of the todo")] string description,
                [Description("Creation date of the todo")] DateTime createdDate)
            {
                var todo = new Todo
                {
                    Description = description,
                    CreatedDate = createdDate
                };
                _db.Todo.Add(todo);
                await _db.SaveChangesAsync();
                return $"Todo created: {todo.Description} (Id: {todo.ID})";
            }
    
            [McpServerTool, Description("Reads all todos, or a single todo if an id is provided.")]
            public async Task<List<Todo>> ReadTodosAsync(
                [Description("Id of the todo to read (optional)")] string? id = null)
            {
                if (!string.IsNullOrWhiteSpace(id) && int.TryParse(id, out int todoId))
                {
                    var todo = await _db.Todo.FindAsync(todoId);
                    if (todo == null) return new List<Todo>();
                    return new List<Todo> { todo };
                }
                var todos = await _db.Todo.OrderBy(t => t.ID).ToListAsync();
                return todos;
            }
    
            [McpServerTool, Description("Updates the specified todo fields by id.")]
            public async Task<string> UpdateTodoAsync(
                [Description("Id of the todo to update")] string id,
                [Description("New description (optional)")] string? description = null,
                [Description("New creation date (optional)")] DateTime? createdDate = null)
            {
                if (!int.TryParse(id, out int todoId))
                    return "Invalid todo id.";
                var todo = await _db.Todo.FindAsync(todoId);
                if (todo == null) return $"Todo with Id {todoId} not found.";
                if (!string.IsNullOrWhiteSpace(description)) todo.Description = description;
                if (createdDate.HasValue) todo.CreatedDate = createdDate.Value;
                await _db.SaveChangesAsync();
                return $"Todo {todo.ID} updated.";
            }
    
            [McpServerTool, Description("Deletes a todo by id.")]
            public async Task<string> DeleteTodoAsync(
                [Description("Id of the todo to delete")] string id)
            {
                if (!int.TryParse(id, out int todoId))
                    return "Invalid todo id.";
                var todo = await _db.Todo.FindAsync(todoId);
                if (todo == null) return $"Todo with Id {todoId} not found.";
                _db.Todo.Remove(todo);
                await _db.SaveChangesAsync();
                return $"Todo {todo.ID} deleted.";
            }
        }
    }
    

    Der obige Code stellt Tools für den MCP-Server mithilfe der folgenden spezifischen Attribute zur Verfügung:

    • [McpServerToolType]: Kennzeichnet die TodosMcpTool Klasse als MCP-Servertooltyp. Es signalisiert dem MCP-Framework, dass diese Klasse Methoden enthält, die als aufrufbare Tools verfügbar gemacht werden sollen.
    • [McpServerTool]: Markiert eine Methode als aufrufbare Aktion für den MCP-Server.
    • [Description]: Diese bieten lesbare Beschreibungen für Methoden und Parameter. Es hilft dem aufrufenden Agent zu verstehen, wie die Aktionen und deren Parameter verwendet werden.

    Dieser Code dupliziert die Funktionalität des vorhandenen TodosController, was unnötig ist, aber du wirst es aus Gründen der Einfachheit beibehalten. Es empfiehlt sich, die App-Logik in eine Dienstklasse zu verschieben und dann die Dienstmethoden sowohl von TodosController als auch aus aufzurufen TodosMcpTool.

  3. Registrieren Sie in Program.cs den MCP-Serverdienst und den CORS-Dienst.

    builder.Services.AddMcpServer()
        .WithHttpTransport() // With streamable HTTP
        .WithToolsFromAssembly(); // Add all classes marked with [McpServerToolType]
    
    builder.Services.AddCors(options =>
    {
        options.AddDefaultPolicy(policy =>
        {
            policy.AllowAnyOrigin()
                  .AllowAnyHeader()
                  .AllowAnyMethod();
        });
    });
    

    Wenn Sie streambare HTTP mit dem MCP-Server verwenden, müssen Sie cross-Origin Resource Sharing (CORS) aktivieren, wenn Sie es mit Clientbrowsertools oder GitHub Copilot (sowohl in Visual Studio Code als auch in GitHub Codespaces) testen möchten.

  4. Aktivieren Sie in Program.cs die MCP- und CORS-Middleware.

    app.MapMcp("/api/mcp");
    app.UseCors();
    

    Dieser Code legt ihren MCP-Serverendpunkt auf <url>/api/mcp.

Testen des MCP-Servers lokal

  1. Führen Sie im Codespace-Terminal die Anwendung mit dotnet run aus.

  2. Wählen Sie im Browser öffnen und dann eine Aufgabe hinzufügen.

    Lassen Sie dotnet run weiterlaufen. Ihr MCP-Server wird zurzeit http://localhost:5093/api/mcp ausgeführt.

  3. Öffnen Sie im Codespace den Copilot-Chat, und wählen Sie dann im Eingabeaufforderungsfeld den Agent-Modus aus.

  4. Wählen Sie die Schaltfläche "Extras " und dann im Dropdownmenü " Weitere Tools hinzufügen" aus.

    Screenshot, der zeigt, wie Sie einen MCP-Server im GitHub Copilot Chat-Agent-Modus hinzufügen.

  5. Wählen Sie "MCP-Server hinzufügen" aus.

  6. Wählen Sie HTTP (HTTP- oder Server-Sent-Ereignisse) aus.

  7. Geben Sie in "Server-URL eingeben"http://localhost:5093/api/mcp ein.

  8. Geben Sie in "Server-ID eingeben" "todos-mcp" oder einen beliebigen Namen ein.

  9. Wählen Sie "Arbeitsbereichseinstellungen" aus.

  10. Geben Sie in einem neuen Copilot-Chatfenster etwas wie "Mir die Todos anzeigen" ein.

  11. Standardmäßig zeigt GitHub Copilot eine Sicherheitsbestätigung an, wenn Sie einen MCP-Server aufrufen. Wählen Sie Weiter aus.

    Screenshot der Standardsicherheitsmeldung eines MCP-Aufrufs in GitHub Copilot Chat.

    Nun sollte eine Antwort angezeigt werden, die angibt, dass der MCP-Toolaufruf erfolgreich ist.

    Screenshot, der die Antwort des MCP-Toolaufrufs im GitHub-Copilot-Chatfenster zeigt.

Bereitstellen Ihres MCP-Servers auf App Service

  1. Stellen Sie ihre Änderungen wieder im Codespace-Terminal bereit, indem Sie Änderungen übernehmen (GitHub Actions-Methode) oder azd up ausführen (Azure Developer CLI-Methode).

  2. Suchen Sie in der AZD-Ausgabe die URL Ihrer App. Die URL sieht in der AZD-Ausgabe wie folgt aus:

     Deploying services (azd deploy)
    
       (✓) Done: Deploying service web
       - Endpoint: <app-url>
     
  3. Öffnen Sie nach Abschluss von azd up.vscode/mcp.json. Ändern Sie die URL in <app-url>/api/mcp.

  4. Wählen Sie oberhalb der geänderten MCP-Serverkonfiguration "Start" aus.

    Screenshot, der zeigt, wie Sie einen MCP-Server manuell aus der lokalen mcp.json Datei starten.

  5. Starten Sie ein neues GitHub Copilot-Chatfenster. Sie sollten in der Lage sein, Aufgaben im Copilot-Agent anzuzeigen, zu erstellen, zu aktualisieren und zu löschen.

Bewährte Sicherheitsmethoden

Wenn Ihr MCP-Server von einem Agent aufgerufen wird, der von großen Sprachmodellen (LLM) unterstützt wird, sollten Sie sich über Eingabeaufforderungsangriffe bewusst sein. Berücksichtigen Sie die folgenden bewährten Sicherheitsmethoden:

  • Authentifizierung und Autorisierung: Sichern Sie Ihren MCP-Server mit der Microsoft Entra-Authentifizierung, um sicherzustellen, dass nur autorisierte Benutzer oder Agents auf Ihre Tools zugreifen können. Eine schrittweise Anleitung finden Sie unter Secure Model Context Protocol-Aufrufe an Azure App Service von Visual Studio Code mit microsoft Entra-Authentifizierung .
  • Eingabeüberprüfung und Bereinigung: Der Beispielcode in diesem Lernprogramm lässt die Eingabeüberprüfung und Bereinigung zur Einfachheit und Klarheit aus. Implementieren Sie in Produktionsszenarien immer die richtige Validierung und Bereinigung, um Ihre Anwendung zu schützen. Informationen zu ASP.NET Core finden Sie unter "Modellüberprüfung" in ASP.NET Core.
  • HTTPS: Das Beispiel basiert auf Azure App Service, der STANDARDMÄßIG HTTPS erzwingt und kostenlose TLS/SSL-Zertifikate zum Verschlüsseln von Daten während der Übertragung bereitstellt.
  • Prinzip der geringsten Rechte: Machen Sie nur die erforderlichen Tools und Daten verfügbar, die für Ihren Anwendungsfall erforderlich sind. Vermeiden Sie das Verfügbarmachen vertraulicher Vorgänge, es sei denn, dies ist erforderlich.
  • Rate Limiting and Throttling: Verwenden Sie API-Verwaltung oder benutzerdefinierte Middleware, um Missbrauch und Denial-of-Service-Angriffe zu verhindern.
  • Protokollierung und Überwachung: Protokollieren des Zugriffs und der Verwendung von MCP-Endpunkten für die Überwachung und Anomalieerkennung. Überwachen Sie verdächtige Aktivitäten.
  • CORS-Konfiguration: Beschränken Sie ursprungsübergreifende Anforderungen auf vertrauenswürdige Domänen, wenn auf Ihren MCP-Server über Browser zugegriffen wird. Weitere Informationen finden Sie unter Aktivieren von CORS.
  • Regelmäßige Updates: Halten Sie Ihre Abhängigkeiten auf dem neuesten Stand, um bekannte Sicherheitsrisiken zu mindern.

Weitere Ressourcen

Integrieren von KI in Ihre Azure App Service-Anwendungen