feat: prominenterer Bestätigungsdialog + move_lesson/delete_lesson (Nutzer-Feedback)
Nach dem ersten Live-Test mit echtem Bridge-Prozess: der bisherige ConfirmDialog fiel zu wenig auf, wenn LehrerApp im Hintergrund lief (Normalfall, da der Anstoß vom KI-Client in einem anderen Fenster kommt). Neuer, eigenständiger McpConfirmDialog statt Änderung am geteilten ConfirmDialog (hätte alle anderen Aufrufer mitbetroffen): breiter, auffälliger Kopfbereich, Topmost. AvaloniaMcpConfirmationService holt das Hauptfenster zusätzlich aus einer möglichen Minimierung und aktiviert es vor dem Anzeigen. move_lesson kapselt die bereits vorhandene LessonSchedulingService.Move (shiftFollowingLessons öffnet eine Lücke für eine neue Stunde, indem spätere Stunden derselben Einheit mitverschoben werden) - keine neue Terminlogik, nur Wiederverwendung. delete_lesson ist eine bewusste, gezielte Ausnahme von "v1 ohne Lösch-Tools" auf expliziten Nutzerwunsch: eigene AllowedDestructiveWriteTools-Liste, Destructive=true-Annotation, Bestätigungstext betont ausdrücklich die fehlende Papierkorb-Deckung für Lessons. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
@@ -8,7 +8,7 @@ using ModelContextProtocol.Server;
|
||||
namespace LehrerApp.Desktop.Services.Mcp;
|
||||
|
||||
/// <summary>
|
||||
/// In-Process-MCP-Server (Phase 1–3, siehe Planungsdokument). Lauscht auf der Named Pipe
|
||||
/// In-Process-MCP-Server (siehe Planungsdokument und TODO.md 4.5.25ff.). Lauscht auf der Named Pipe
|
||||
/// <see cref="McpPipeConstants.PipeName"/> und bedient jede eingehende Verbindung (eine je
|
||||
/// LehrerApp.McpBridge-Instanz) als eigene MCP-Session über <see cref="StreamServerTransport"/> —
|
||||
/// ein <see cref="NamedPipeServerStream"/> ist ein normaler <see cref="Stream"/> und kann direkt
|
||||
@@ -129,7 +129,8 @@ public sealed class McpServerHostedService : IAsyncDisposable
|
||||
|
||||
// Write-Tools schreiben nie direkt - jede Handler-Methode ruft selbst erst
|
||||
// IMcpConfirmationService auf (siehe die jeweilige Tool-Klasse). ReadOnly bewusst false,
|
||||
// Destructive bewusst false (keine der Phase-2-Schreiboperationen löscht etwas).
|
||||
// Destructive bewusst false (keine dieser Schreiboperationen löscht etwas) - für die
|
||||
// Ausnahme siehe AddDestructiveWriteTool/McpToolScope.AllowedDestructiveWriteTools.
|
||||
void AddWriteTool(Delegate handler, string name, string description)
|
||||
{
|
||||
toolCollection.Add(McpServerTool.Create(handler, new McpServerToolCreateOptions
|
||||
@@ -141,6 +142,17 @@ public sealed class McpServerHostedService : IAsyncDisposable
|
||||
}));
|
||||
}
|
||||
|
||||
void AddDestructiveWriteTool(Delegate handler, string name, string description)
|
||||
{
|
||||
toolCollection.Add(McpServerTool.Create(handler, new McpServerToolCreateOptions
|
||||
{
|
||||
Name = name,
|
||||
Description = description,
|
||||
ReadOnly = false,
|
||||
Destructive = true,
|
||||
}));
|
||||
}
|
||||
|
||||
AddReadTool(studentTools.GetStudents, "get_students",
|
||||
"Listet Schüler, optional gefiltert nach Lerngruppe.");
|
||||
AddReadTool(examTools.GetExams, "get_exams",
|
||||
@@ -182,10 +194,16 @@ public sealed class McpServerHostedService : IAsyncDisposable
|
||||
"Entfernt eine Verlaufsplan-Phase aus einer Einzelstunde (Bestätigung durch den Nutzer nötig).");
|
||||
AddWriteTool(lessonPlanTools.AddLessonAttachment, "add_lesson_attachment",
|
||||
"Fügt einer Einzelstunde ein neues Material als Base64-kodierten Anhang hinzu (Bestätigung durch den Nutzer nötig).");
|
||||
AddWriteTool(lessonPlanTools.MoveLesson, "move_lesson",
|
||||
"Verschiebt eine Einzelstunde auf ein neues Datum, optional mit Mitverschieben späterer Stunden derselben Einheit (Bestätigung durch den Nutzer nötig).");
|
||||
|
||||
AddDestructiveWriteTool(lessonPlanTools.DeleteLesson, "delete_lesson",
|
||||
"Löscht eine Einzelstunde endgültig, ohne Papierkorb (Bestätigung durch den Nutzer nötig).");
|
||||
|
||||
System.Diagnostics.Debug.Assert(
|
||||
toolCollection.Select(t => t.ProtocolTool.Name).OrderBy(n => n)
|
||||
.SequenceEqual(McpToolScope.AllowedReadTools.Concat(McpToolScope.AllowedWriteTools).OrderBy(n => n)),
|
||||
.SequenceEqual(McpToolScope.AllowedReadTools.Concat(McpToolScope.AllowedWriteTools)
|
||||
.Concat(McpToolScope.AllowedDestructiveWriteTools).OrderBy(n => n)),
|
||||
"Registrierte MCP-Tools weichen von McpToolScope ab.");
|
||||
|
||||
return new McpServerOptions
|
||||
|
||||
Reference in New Issue
Block a user