MCP Fusion/Protocol and runtime/Prompt-Engine
Prompt-Engine
Prompts sind gleichberechtigte Bürger neben Tools: typisierte Argument-Schemas, Loopback-Ausführung von Tools aus Prompt-Handlern, Paginierung mit signierten Cursors, Interceptors und Hydration-Deadlines.
Tools führen aus; Prompts säen. Ein Prompt ist eine wiederverwendbare serverseitige Vorlage für eine Konversation: Der Client listet sie auf, der Nutzer wählt eine aus, und der Server liefert die Nachrichtenserie zurück. MCP Fusion behandelt sie mit demselben Engineering wie Tools: typisierte Eingaben, Middleware, Paginierung und ein Loopback in Ihre eigene Tool-Pipeline.
Einen Prompt definieren
import { z } from 'zod';
export default f.prompt('issue.review')
.describe('Review a pull request with the team checklist')
.input(z.object({
repo: z.string().describe('Repository slug'),
pr: z.number().describe('Pull request number'),
}))
.handler(async (ctx, args) => ({
description: 'Review acme/product#42 against the checklist',
messages: [
{ role: 'user', content: `Review PR ${args.pr} in ${args.repo}. Use the checklist.` },
{ role: 'assistant', content: 'Sharing the checklist first, then the diff.' },
],
}));Die Fluent-Form spiegelt die der Tools: .describe(), .input() (ein Zod-Objekt, oder eine flache Descriptor-Map mit primitiven Argumenten), .use(middleware), .title(), .icons(), .tags() und als Abschluss .handler((ctx, args) => PromptResult). Das Ergebnis ist { description?, messages } mit den Rollen user und assistant, mehrere Turns sind erlaubt, und es gibt Inhaltsblöcke über Text hinaus: image, audio, resource_link, resource und die Factory-Helfer von PromptMessage (.system() wird als user kodiert: MCP hat keine system-Rolle).
Die deklarative Form, definePrompt, und die f.prompt(name, config)-Form im Stil von f.presenter() existieren für Config-as-Code-Layouts. Argumente werden mit strikter flacher Validierung nach Zod kompiliert: nur Primitives, keine Arrays oder verschachtelten Objekte. Das ist eine Vorgabe von MCP, durchgesetzt zur Definitionszeit mit einer klaren Fehlermeldung statt erst auf dem Wire.
Loopback: Prompts, die Tools aufrufen
Der Kontext des Prompt-Handlers enthält invokeTool(name, args), einen Dispatcher in dieselbe Tool-Pipeline mit Middleware, Validierung und Presenters. Ein Prompt ist daher kein statischer String: Er kann mit den Tools des Nutzers selbst den Live-Diff des PR abrufen, die Checkliste hydratisieren und erst dann die gesetzten Nachrichten zurückgeben. RBAC wird im Loopback durchgesetzt (der Kontext des Aufrufenden ist der Kontext des Aufrufenden), und das AbortSignal der Anfrage wird durchgereicht, sodass ein abgebrochener Prompt die von ihm ausgelöste Tool-Arbeit abbricht.
Die Hydration ist begrenzt: eine Frist pro Registry (.timeout(ms) am Builder oder setDefaultHydrationTimeout) deckelt, wie lange ein Prompt damit verbringen darf, Tools aufzurufen, bevor er zurückgibt. Nach Ablauf der Frist wird die Antwort mit einem Hydration-Alarm-Block ausgeliefert, statt den Client hängen zu lassen.
Paginierung und Lebenszyklus
prompts/list wird serverseitig paginiert: CursorCodec wandelt den „after"-Namen in einen Cursor um, der entweder mit HMAC-SHA256 signiert oder mit AES-GCM verschlüsselt ist (konfiguriert mit einem 32-Byte-Secret; ohne eines gilt ein prozesseigener ephemerer Schlüssel). Die Seitengröße ist standardmäßig 50, Filterung nach Tags wird unterstützt. Ein Cursor ist für Clients bewusst opak.
notifyPromptListChanged() (oder der list_changed-Ereignispfad bei f.prompt-Mutationen zur Laufzeit) sendet notifications/prompts/list_changed, entprellt auf 100 ms, damit eine Registry, die während einer Sitzung wächst, den Client nicht zuschüttet.
Interceptors
registry.useInterceptor(fn) läuft nach der Rückgabe eines Handlers und bevor der Client das Ergebnis sieht: einen <compliance_notice> anhängen, einen Nutzer-Turn voranstellen oder Kontextblöcke injizieren, die in ein Tag gehüllt sind. Intercepting ist der sichere Weg, organisationsweite Vorgaben hinzuzufügen, ohne jeden Prompt anzufassen.
Warum das zählt
Die Integrationssteuer für Teams, die auf MCP aufbauen, lautet meist „der Client hat nur Tools". Prompts schließen die andere Hälfte: Sie liefern den Workflow, nicht nur die Fähigkeit. Zusammen mit Tools, Resources und dem Wire format kann ein einzelner Connector einem Agenten die gesamte Form an die Hand geben, wie mit Ihren Daten zu arbeiten ist, im nativen Protokoll des Agenten.
Nächste Schritte
- Tools: die Ausführungshälfte
- Runtime architecture: wo die Registry sitzt
- Skills: Prompts sind auch der Weg, wie SKILL.md zu Agenten kommt
