Zeitlich begrenzt

2026 OpenAI Structured Outputs: JSON Schema stabil ausgeben

Blog AIDevelopment
2026-08-20 ca. 14 Min. Lesezeit

Dieser Leitfaden zeigt Backend-Entwicklern, wie sie OpenAI Structured Outputs als belastbaren Vertrag für Datenbanken, Workflows und Tool-Ausführer einsetzen. Sie erhalten eine zeitlich geordnete Umsetzung mit Schema-Entwurf, strikter API-Konfiguration, Fehlerbehandlung, semantischer Validierung und Versionspflege.

Kernaussagen

  1. Eine API-Antwort sieht zwar wie gültiges JSON aus, lässt sich aber wegen fehlender Felder, Ablehnung oder abgeschnittenem Inhalt nicht sicher speichern.
  2. Die schnellste belastbare Lösung: Verwenden Sie OpenAI Structured Outputs mit einem bewusst kleinen, strikten JSON Schema und prüfen Sie danach API-Status, Abschlussgrund sowie Geschäftsregeln in Ihrer Anwendung.
2026 OpenAI Structured Outputs: JSON Schema stabil ausgeben
2026 OpenAI Structured Outputs: JSON Schema stabil ausgeben

Eine API-Antwort sieht zwar wie gültiges JSON aus, lässt sich aber wegen fehlender Felder, Ablehnung oder abgeschnittenem Inhalt nicht sicher speichern.

Die schnellste belastbare Lösung: Verwenden Sie OpenAI Structured Outputs mit einem bewusst kleinen, strikten JSON Schema und prüfen Sie danach API-Status, Abschlussgrund sowie Geschäftsregeln in Ihrer Anwendung.

Für wen dieser Leitfaden gedacht ist

Dieser Beitrag richtet sich an Backend-Entwickler, die Antworten direkt in Datenbanken, Automatisierungen oder Tool-Ausführer übergeben möchten. Wenn Sie lediglich lesbares JSON für eine Anzeige benötigen, reicht möglicherweise eine weniger strenge Lösung.

Besonders relevant ist der Leitfaden für drei Gruppen: Entwickler, die JSON mode ersetzen, Teams mit Datenextraktionspipelines und Verantwortliche für Projekte mit Function Calling. Für jede dieser Gruppen liegt die eigentliche Stabilität nicht nur im Modell, sondern im Zusammenspiel aus Vertrag, API-Konfiguration und eigener Prüfung.

Der Ausgabevertrag vor dem ersten Request

Bevor Sie einen Prompt formulieren, verfolgen Sie den Datenfluss rückwärts. Welche Felder benötigt der nächste Dienst tatsächlich? Welche Werte schreibt die Datenbank, welche Werte werden nur geloggt, und welche Informationen gehören ausschließlich in eine menschliche Erläuterung?

Ein gutes Schema beantwortet diese Fragen ausdrücklich:

  • Pflichtfelder: Ein Feld ist erforderlich, wenn der nachgelagerte Prozess ohne dieses Feld nicht sicher weiterarbeiten kann.
  • Optionale Informationen: Verwenden Sie Nullable-Felder nur dann, wenn „nicht vorhanden“ fachlich etwas anderes bedeutet als ein leerer String.
  • Enums: Begrenzen Sie Statuswerte, Kategorien und Aktionsarten auf bekannte Werte. Freitext an dieser Stelle erzeugt später zusätzliche Prüf- und Mappingarbeit.
  • Datentypen: Legen Sie fest, ob ein Wert als String, Zahl, Boolean oder Liste verarbeitet wird. Ein Datum als Text benötigt zusätzlich eine fachliche Formatprüfung.
  • Zusätzliche Eigenschaften: Bei einem Datenbank- oder Toolvertrag ist additionalProperties: false meist die sichere Wahl, sofern der verwendete OpenAI-Endpunkt und der gewählte Modus diese Vorgabe unterstützen.
  • Trennung von Inhalt und Erklärung: Speichern Sie keine Begründung in einem Feld, das eigentlich eine ausführbare Aktion beschreibt. Ein Tool-Aufruf sollte die für das Tool benötigten Parameter enthalten, nicht die gesamte Modellantwort.

OpenAI beschreibt in der offiziellen Einführung zu Structured Outputs und JSON Schema, dass die strukturierte Ausgabe an ein Schema gebunden werden kann. Für Ihre Architektur bedeutet das nicht, dass jedes denkbare Ergebnis in ein gigantisches Schema gehört. Ein kleiner Vertrag mit wenigen stabilen Feldern ist leichter zu testen, zu versionieren und bei Änderungen abwärtskompatibel zu halten.

Ein konkreter Datenfluss

Nehmen wir eine Support-Weiterleitung. Die Anwendung erhält einen unstrukturierten Nachrichtentext und soll eine interne Routing-Entscheidung erzeugen. Das Datenobjekt könnte die Felder category, priority, needs_human und summary enthalten. Eine ausführliche Begründung gehört nicht in priority; sie wäre entweder ein eigenes, nicht ausführbares Feld oder verbleibt außerhalb des Maschinenvertrags.

So vermeiden Sie eine häufige Fehlkonstruktion: Das Modell liefert zwar formal ein Objekt, aber ein einzelnes Feld enthält gleichzeitig Status, Erklärung und Handlungsanweisung. Der Parser akzeptiert diesen Text, während der nachfolgende Workflow ihn nicht zuverlässig auswerten kann.

Konfiguration der ersten Anfrage

Bei OpenAI Structured Outputs müssen Sie zwischen der endgültigen Antwort und den Parametern eines Werkzeugs unterscheiden. Ein strukturiertes Endergebnis wird im Antwortformat des Requests konfiguriert. Bei Function Calling liegt das Schema dagegen in der Definition des Tools, also bei dessen Parametern.

Für die Responses API sollte Ihr Code die aktuell dokumentierte Struktur verwenden und keine ältere Chat-Completion-Konfiguration mit einer neuen Request-Form vermischen. Die OpenAI-Referenz zur Responses API ist die maßgebliche Stelle, wenn sich Feldnamen oder SDK-Aufrufe ändern.

Ein minimales JavaScript-Muster für eine direkte strukturierte Antwort sieht sinngemäß so aus:

const response = await client.responses.create({
  model: process.env.OPENAI_MODEL,
  input: [
    {
      role: "user",
      content: "Ordnen Sie diese Nachricht einer Kategorie zu: ..."
    }
  ],
  text: {
    format: {
      type: "json_schema",
      name: "routing_result",
      strict: true,
      schema: {
        type: "object",
        properties: {
          category: {
            type: "string",
            enum: ["billing", "technical", "account"]
          },
          priority: {
            type: "string",
            enum: ["low", "normal", "high"]
          },
          needs_human: {
            type: "boolean"
          },
          summary: {
            type: "string"
          }
        },
        required: [
          "category",
          "priority",
          "needs_human",
          "summary"
        ],
        additionalProperties: false
      }
    }
  }
});

Die konkrete Modellwahl sollten Sie nicht aus einem alten Beispiel übernehmen. Prüfen Sie vor dem Einsatz die aktuelle Modellobjekt-Referenz und halten Sie Modellname, API-Endpunkt und Schema gemeinsam in Ihrer Testmatrix fest.

Für Function Calling sieht die Position des Vertrags anders aus:

const response = await client.responses.create({
  model: process.env.OPENAI_MODEL,
  input: "Ermitteln Sie die Lieferadresse des Kunden.",
  tools: [
    {
      type: "function",
      name: "lookup_delivery_address",
      description: "Sucht eine bestätigte Lieferadresse.",
      strict: true,
      parameters: {
        type: "object",
        properties: {
          customer_id: { type: "string" }
        },
        required: ["customer_id"],
        additionalProperties: false
      }
    }
  ]
});

Das Beispiel zeigt die entscheidende Abgrenzung: Das erste Schema beschreibt die Antwort, die Ihre Anwendung konsumiert. Das zweite beschreibt Argumente für einen aufrufbaren Dienst. Beide Verträge können strikt sein, aber sie lösen unterschiedliche Architekturprobleme.

Vergleich der geeigneten Modi

OptionStrukturelle ZusageGeeigneter EinsatzVerbleibendes RisikoIhre Entscheidung
Freie TextantwortKeine feste ObjektstrukturDialog, Zusammenfassung, redaktioneller EntwurfParsing und FormatabweichungenNur bei menschlicher Prüfung
JSON modeGültiges JSON als ZielEinfache JSON-Ausgabe ohne engen VertragFehlende Felder, falsche Typen oder unerwartete SchlüsselNicht als Datenbankvertrag behandeln
Structured OutputsBindung an ein unterstütztes JSON SchemaExtraktion, Datenbankeintrag, WorkflowSemantik, Ablehnung und Abbruch müssen Sie prüfenFür produktive Maschinenübergaben bevorzugen
Function Calling mit strictStrukturierte Tool-ParameterKontrollierte API- oder Tool-AufrufeBerechtigung, Identität und fachliche PlausibilitätVor Ausführung serverseitig validieren

Die Tabelle ist eine Entscheidungsunterstützung, keine Garantieerklärung. Auch bei strikter Struktur kann category zwar ein erlaubter Enum-Wert sein, aber für den konkreten Text fachlich falsch gewählt werden.

Prüfpfad nach dem Empfang

Verarbeiten Sie eine Antwort nicht unmittelbar mit JSON.parse und schreiben Sie sie danach in die Datenbank. Ein sicherer Ablauf besteht aus einer technischen Prüfung und einer fachlichen Prüfung.

Technische Prüfung

Zuerst kontrollieren Sie, ob die API-Anfrage erfolgreich war. Danach prüfen Sie, ob eine Ablehnung vorliegt, ob die Ausgabe vollständig beendet wurde und ob überhaupt der erwartete Inhaltstyp eingetroffen ist. Bei Streaming müssen Sie die Ereignisse korrekt zusammensetzen; die Dokumentation zu Refusal-Deltas in der Responses API ist dafür wichtiger als ein selbst erdachtes String-Muster.

Eine unterbrochene Antwort ist kein teilweise gültiges Geschäftsobjekt. Wenn die Verbindung abbricht oder die Ausgabe wegen eines Längenlimits endet, markieren Sie den Datensatz als unvollständig. Wiederholen Sie nicht blind, wenn die Anfrage möglicherweise bereits eine externe Nebenwirkung ausgelöst hat.

Fachliche Prüfung

Anschließend validiert Ihre Anwendung die Werte gegen Regeln, die das JSON Schema nicht ausdrücken kann oder die Sie bewusst nicht in das Schema aufgenommen haben. Beispiele:

  • Ein Enddatum darf nicht vor dem Startdatum liegen.
  • Eine ausgewählte Kategorie muss zum Mandanten oder Produktbereich gehören.
  • Eine Tool-Aktion darf nur für den authentifizierten Benutzer ausgeführt werden.
  • Eine extrahierte Kundennummer muss in Ihrem System existieren.
  • Eine Zusammenfassung darf keine vertraulichen Inhalte in ein öffentliches Ziel übertragen.

Schema-Konformität bedeutet also: Die Antwort hat die erwartete Form. Sie bedeutet nicht: Die Antwort ist wahr, berechtigt oder für eine irreversible Aktion geeignet. Diese Trennung ist bei einem automatischen Datenbankimport wichtiger als die Frage, ob der JSON-Text syntaktisch korrekt ist.

Fehlerklassen und Reaktionen

Nicht unterstütztes Schema

Ein Schema kann durch verschachtelte Varianten, bestimmte Schlüsselwörter oder eine zu umfangreiche Modellierung mit dem gewählten Endpunkt inkompatibel sein. Behandeln Sie das als Konfigurationsfehler, nicht als Modellversagen. Reduzieren Sie das Schema auf die wirklich benötigten Eigenschaften, ersetzen Sie problematische Varianten durch klarere Enums oder teilen Sie den Prozess in fachlich getrennte Antworten.

Protokollieren Sie dabei die Schema-Version. Ohne diesen Kontext können Sie später nicht feststellen, ob ein Fehler nach einer Schemaänderung oder nach einer Änderung von Modell und Endpunkt auftrat.

Kompilierung und Verzögerung

Ein neues Schema kann beim Dienst zunächst verarbeitet werden. Deshalb sollten Sie nicht ausschließlich die Latenz des ersten Requests als repräsentativ für den Dauerbetrieb bewerten. Führen Sie vor dem produktiven Verkehr einen kontrollierten Vorlauf mit genau der später verwendeten Schema-Version durch und nehmen Sie Änderungen nur über Ihre Testumgebung an.

Eine optimierte Struktur hilft auch operativ: Entfernen Sie ungenutzte Felder, vermeiden Sie unnötige Verschachtelung und halten Sie verschiedene Anwendungsfälle in getrennten Verträgen. Das verbessert nicht automatisch jede Anfrage, macht Fehler aber deutlich lokalisierbarer.

Abbruch durch Länge oder Transport

Bei langen Eingaben und umfangreichen Ausgaben müssen Sie den Abschlussstatus und die tatsächlich erhaltenen Inhalte prüfen. Ein Parser kann einen Fragmentrest ablehnen; ein toleranter Parser kann dagegen scheinbar brauchbare, aber unvollständige Werte liefern. Für Datenbank- und Toolpfade ist die zweite Situation gefährlicher.

Markieren Sie einen Abbruch als wiederholbar, wenn der Request idempotent ist. Bei nicht idempotenten Operationen darf die Wiederholung erst nach einer Prüfung erfolgen, ob der externe Dienst bereits erreicht wurde. Eine erneute Modellanfrage ist kein Ersatz für ein Transaktionskonzept.

Ablehnung

Eine Ablehnung ist ein eigener Zustand. Führen Sie den Inhalt nicht als normales Ergebnis weiter und speichern Sie ihn nicht in Felder, die nachgelagerte Systeme als geprüfte Fachdaten interpretieren. Je nach Anwendungsfall können Sie eine neutrale Rückmeldung ausgeben, den Auftrag mit sicherer Eingrenzung erneut bewerten oder den Vorgang einer manuellen Warteschlange zuführen.

Bei sicherheitskritischen Prozessen muss die Standardaktion bei unklarer Antwort „nicht ausführen“ lauten. Das gilt auch dann, wenn alle übrigen Felder formal dem Schema entsprechen.

Geschäftsregel verletzt

Ein fachlich unplausibles Objekt ist weder durch strict noch durch einen erfolgreichen Parser geheilt. Legen Sie deshalb einen eigenen Fehlerstatus an, speichern Sie die minimal erforderlichen Diagnoseinformationen und entscheiden Sie zwischen Korrekturanfrage, erneuter Extraktion mit engerem Kontext und manueller Prüfung.

Die Entscheidung sollte vom Schaden einer falschen Aktion abhängen. Eine falsch zugeordnete interne Markierung kann anders behandelt werden als eine Zahlung, eine Kontosperre oder eine Änderung an einem produktiven System.

FAQ zur Umsetzung

Die folgenden Antworten ergänzen den Ablauf um typische Migrations- und Entwurfsentscheidungen.

Wie stellt OpenAI die Einhaltung eines JSON Schema sicher?

OpenAI Structured Outputs verwendet ein angegebenes und unterstütztes Schema als strukturellen Vertrag, wenn Sie das passende Format mit aktiviertem striktem Modus konfigurieren. Das verhindert viele Abweichungen bei Schlüsseln, Typen und Pflichtfeldern. Es ersetzt jedoch keine fachliche Prüfung: Ein formal erlaubter Enum-Wert kann für den konkreten Datensatz trotzdem falsch sein.

Structured Outputs und JSON mode

JSON mode und Structured Outputs sollten nicht als gleichwertige Namen für dieselbe Funktion behandelt werden. JSON mode zielt auf gültiges JSON, während Structured Outputs die erwartete Objektstruktur enger festlegt. Wenn ein Importprozess bestimmte Pflichtfelder und Datentypen benötigt, ist ein Schema-Vertrag die passendere Wahl. Für reine Darstellung oder nachgelagerte menschliche Bearbeitung kann JSON mode weiterhin genügen.

strict true und Parsing-Fehler

strict: true schützt nur den jeweils konfigurierten strukturellen Vertrag. Ein Fehler kann aus einer Ablehnung, einem abgeschnittenen Stream, einem nicht unterstützten Schema, einem falschen Zugriffspfad im SDK oder einer eigenen fachlichen Validierung stammen. Deshalb sollte Ihr Fehlerprotokoll diese Ursachen getrennt erfassen, anstatt jeden Fehler als „ungültiges JSON“ zu etikettieren.

Umgang mit Ablehnungen

Ihre Anwendung sollte den Ablehnungszustand vor dem Parsen des erwarteten Geschäftsobjekts erkennen. Danach entscheiden Sie anhand des Risikos über sichere Rückgabe, begrenzte Wiederholung oder manuelle Bearbeitung. Ein leerer Ersatzdatensatz ist keine sichere Behandlung, weil er in vielen Datenbanken wie eine bestätigte, aber inhaltslose Antwort aussehen kann.

Vereinfachung eines komplexen Schemas

Beginnen Sie mit dem kleinsten Objekt, das der nächste Verarbeitungsschritt wirklich benötigt. Teilen Sie optionale oder unabhängige Ergebnisse auf, statt viele Alternativen in einer tief verschachtelten Struktur zu bündeln. Danach testen Sie jede Teilantwort separat und prüfen, ob die Zusammenführung in Ihrer Anwendung atomar und nachvollziehbar bleibt.

Regression vor dem Produktivbetrieb

Erstellen Sie eine feste Sammlung von Testfällen, bevor Sie das Schema für echte Daten freischalten. Die Sammlung sollte normale Eingaben ebenso enthalten wie Grenzfälle, fehlende Angaben, leere Werte, sehr lange Texte und Fälle, in denen eine sichere Ablehnung erwartet wird. Ergänzen Sie Beispiele, bei denen zwei Felder nur gemeinsam gültig sind; gerade diese Regeln werden häufig nicht vollständig im JSON Schema ausgedrückt.

Für jeden Lauf speichern Sie mindestens:

  • Modellbezeichnung und verwendeten API-Endpunkt,
  • Schema-Namen und Schema-Version,
  • Version des eigenen Parsers beziehungsweise Validierers,
  • Eingabeklasse und erwarteten Abschlussstatus,
  • technische Prüfergebnisse und fachliche Prüfergebnisse,
  • Entscheidung über Wiederholung, Quarantäne oder Freigabe.

Nutzen Sie für Tests anonymisierte oder künstlich erzeugte Daten. OpenAI beschreibt in den Hinweisen zu Datenkontrollen nach Endpunkt, welche Datenverarbeitungsfragen Sie je nach Nutzung berücksichtigen müssen. Für Sie kommen zusätzlich DSGVO-Anforderungen, Aufbewahrungsfristen, Zugriffskontrollen und die Trennung von Test- und Produktionsdaten hinzu.

Ein Regressionstest sollte nicht nur den Idealfall bestätigen. Er muss auch beweisen, dass Ihre Anwendung bei Ablehnung, unvollständigem Empfang und fachlich falschem, aber formal gültigem Inhalt nicht automatisch weiterarbeitet. Erst diese Negativfälle machen den Test für einen produktiven Workflow wertvoll.

Schema-Versionierung und Betrieb

Behandeln Sie Ihr JSON Schema wie einen API-Vertrag. Eine Änderung an einem Pflichtfeld oder Enum ist keine rein interne Prompt-Anpassung, wenn bereits Datenbanken, Queue-Consumer oder Tool-Ausführer davon abhängen.

Eine robuste Versionierungsstrategie umfasst:

  • eine unverwechselbare Schema-ID oder Versionsbezeichnung,
  • Kompatibilitätsprüfung vor dem Merge,
  • getrennte Verarbeitung alter und neuer Datensätze, falls nötig,
  • kontrollierte Freigabe für einen begrenzten Datenstrom,
  • Rückweg zu einem bekannten Vertrag,
  • Überwachung von Ablehnungen, Abbrüchen und fachlichen Fehlern.

Neue optionale Felder sind häufig leichter einzuführen als eine Umbenennung oder Entfernung. Trotzdem muss auch eine scheinbar kleine Ergänzung geprüft werden, weil sie Kompilierungsverhalten, Antwortgröße, Parserannahmen und nachgelagerte Serialisierung beeinflussen kann.

Für Streaming und Batchverarbeitung gelten zusätzlich unterschiedliche Betriebsrisiken. Streaming reduziert nicht automatisch die fachliche Unsicherheit; es verlangt vielmehr eine saubere Zustandsmaschine, die Teilstücke sammelt und erst nach einem bestätigten Abschluss weitergibt. Bei Batchläufen benötigen Sie eine Wiederholungsstrategie, die Duplikate verhindert und bereits verarbeitete Einträge erkennt.

Wenn Sie diese Prüfungen in einer CI/CD-Pipeline ausführen, sollte jede Schemaänderung dieselben positiven und negativen Beispielsätze durchlaufen. Bewahren Sie die Testausgabe zusammen mit den Versionen auf, damit ein späterer Fehler reproduzierbar bleibt. Die offizielle OpenAI-Einführung zu Structured Outputs eignet sich als Referenz für die Grundidee; für die konkrete Implementierung müssen Sie jedoch die zum verwendeten Endpunkt passende aktuelle Dokumentation heranziehen.

Entscheidungsrahmen für Ihre Architektur

Wählen Sie Structured Outputs, wenn ein nachgelagerter Dienst ein definiertes Objekt benötigt und Sie bereit sind, Ablehnungen, Abbrüche und fachliche Fehler als eigene Zustände zu behandeln. Bleiben Sie bei freier Ausgabe, wenn ein Mensch den Inhalt vollständig prüft und keine Maschine daraus eine Aktion ableitet. Verwenden Sie JSON mode nur dort, wo gültiges JSON genügt und die Anwendung fehlende oder zusätzliche Felder sicher tolerieren kann.

Für Werkzeugaufrufe gilt eine zusätzliche Grenze: Ein korrektes Function Calling-Argument ist noch keine Berechtigung. Der Server muss Identität, Zugriff, Eingabewerte, Idempotenz und erwartete Nebenwirkungen unabhängig vom Modell prüfen. Das Schema validiert die Form; Ihre Anwendung entscheidet, ob die Aktion zulässig ist.

Wenn Ihre bisherigen JSON-Fehler vor allem aus wechselnden Schlüsseln und Datentypen stammen, migrieren Sie zuerst einen klar abgegrenzten Pfad. Wenn die Fehler dagegen aus falschen Zuordnungen, unvollständigen Quellen oder riskanten Tool-Aktionen kommen, wird ein striktes Schema allein die Ursache nicht beseitigen. Planen Sie dann vor der Umstellung die semantische Validierung und die Fehlerwarteschlange.

Fazit und nächster Umsetzungsschritt

Für produktive Datenübergaben ist OpenAI Structured Outputs dem bloßen Prompt „Geben Sie JSON zurück“ überlegen, aber nur als Teil einer kontrollierten Kette. Der belastbare Ansatz beginnt mit einem kleinen JSON Schema, trennt Antwortformat und Function Calling-Parameter, prüft technische Zustände vor dem Parsen und validiert danach die Geschäftslogik. Regressionstests und Schema-Versionierung entscheiden, ob diese Lösung auch nach API-, Modell- oder Anwendungsänderungen nachvollziehbar bleibt.

Wenn Sie dafür zunächst eine neutrale Abnahmevorlage ohne Kundendaten benötigen, können Sie die passende Dokumentations- und Hilfeseite von kvmboot als Ausgangspunkt für Ihre Prüfschritte verwenden. Für größere Testmatrizen, parallele CI/CD-Läufe oder reproduzierbare Integrationsprüfungen kann eine temporär gemietete Mac-Umgebung sinnvoller sein als Ihr einzelner Arbeitsplatz: Ihr aktueller Rechner bindet Tests an lokale Ressourcen, erschwert parallele Betriebssystem- und Netzwerkprüfungen und kann durch manuelle Umgebungsänderungen die Reproduzierbarkeit verschlechtern. Eine kvmboot-Mietumgebung bietet Ihnen dafür einen getrennten Testort, ohne dass Sie für einen kurzfristigen Validierungslauf zusätzliche Hardware dauerhaft anschaffen müssen. Prüfen Sie vorab jedoch, ob Sie langfristige Dauerlast, spezielle physische Schnittstellen oder lokale Geheimnisverwaltung benötigen; in diesen Fällen kann ein eigener Rechner die passendere Wahl bleiben. Für eine zeitlich begrenzte, wiederholbare Testphase finden Sie die verfügbaren Mac-Mietoptionen von kvmboot.

Ihre stabile Entwicklungsumgebung für strukturierte Daten

Mit einem gemieteten Mac von kvmboot testen Sie JSON-Schema-Validierungen und Backend-Workflows in einer zuverlässigen Remote-Umgebung.

Pläne ansehen · Startseite

Structured Output, JSON Schema und JSON im direkten Vergleich · JSON Schema als Werkzeugvertrag für KI-Agenten und MCP