{ }
GET
OpenAPI · API-First · Code-First · API Design · Workflow
OpenAPI-First vs. Code-First
Welcher Workflow für welches Team?

Die Wahl zwischen OpenAPI-First und Code-First ist keine technische, sondern eine organisatorische Entscheidung. Sie hängt von Teamgröße, Produktreife, Konsumenten-Anzahl und Synchronisationsanforderungen ab. Dieser Guide liefert einen strukturierten Entscheidungsrahmen – mit konkreten Tooling-Empfehlungen für beide Ansätze.

14 Min. Lesezeit OpenAPI-First · Code-First · API Gateway · Codegen · Contract Testing Symfony · PHP · NelmioApiDoc · openapi-generator

1. Was OpenAPI-First und Code-First bedeuten

Beim Code-First Ansatz wird die API im Code implementiert und die OpenAPI-Spezifikation wird danach – oft automatisch – aus Annotationen, Attributen oder Reflection generiert. Die Spezifikation ist ein Nebenprodukt des Codes. Beim OpenAPI-First Ansatz (auch API-First oder Design-First genannt) wird die Spezifikation zuerst geschrieben, dann wird daraus Code generiert – Server-Stubs, Client-SDKs und Validierungs-Middleware. Die Spezifikation ist die Quelle der Wahrheit, Code ist ein Nebenprodukt der Spec.

Diese scheinbar technische Unterscheidung hat fundamentale organisatorische Konsequenzen. Code-First bedeutet: Die Schnittstelle ist das Ergebnis von Implementierungsentscheidungen. Ein Framework-Default, eine Namenskonvention oder ein Refactoring ändern die API. OpenAPI-First bedeutet: Die Schnittstelle ist eine explizite Entscheidung. Änderungen an der API erfordern eine bewusste Änderung der Spezifikation, die dann als Change-Request diskutiert und genehmigt werden kann. Welcher Ansatz besser ist, hängt vollständig vom Kontext ab.

Es gibt auch hybride Ansätze: Code-First mit strikten Linting-Regeln und Contract-Tests, die sicherstellen, dass die generierte Spec den definierten Standards entspricht. Oder OpenAPI-First für die initiale API-Definition, danach Code-First für inkrementelle Erweiterungen mit automatischer Spec-Generierung und Drift-Detection. Die sauberste Lösung in großen Teams ist jedoch fast immer reines OpenAPI-First mit klarer Governance für Spec-Änderungen.

2. Code-First: Stärken, Schwächen und wann er passt

Der größte Vorteil von Code-First ist die Entwicklungsgeschwindigkeit in frühen Phasen. Ein Team, das schnell iterieren muss und noch nicht genau weiß, wie die API aussehen soll, kann Endpoints implementieren, ausprobieren und wieder ändern – ohne jedes Mal zuerst eine Spec zu aktualisieren. Die Dokumentation entsteht automatisch und ist immer synchron mit dem Code. Kein YAML anfassen, kein manuelles Update nach Refactorings.

Die Schwächen zeigen sich mit wachsender API-Größe und Konsumenten-Anzahl. Die generierte Spec spiegelt Implementierungsdetails wider, nicht das gewünschte API-Design. Felder heißen so wie Datenbankfelder oder Klassen-Properties, nicht so wie es für Konsumenten sinnvoll wäre. Breaking Changes passieren versehentlich durch Refactoring. Mehrere Teams können keine parallele Frontend/Backend-Entwicklung beginnen, weil die API erst existieren muss bevor sie konsumiert werden kann. Für interne APIs in kleinen, agilen Teams ist Code-First jedoch oft die pragmatischere Wahl.


# Code-First in Symfony mit NelmioApiDocBundle — Attribute-basierte Annotation

namespace App\Controller\Api;

use Nelmio\ApiDocBundle\Annotation\Model;
use OpenApi\Attributes as OA;
use Symfony\Component\Routing\Attribute\Route;
use Symfony\Component\HttpFoundation\JsonResponse;

#[OA\Tag(name: 'orders')]
#[Route('/api/v2/orders', name: 'api_')]
class OrderController extends AbstractApiController
{
    #[Route('', name: 'orders_create', methods: ['POST'])]
    #[OA\Post(
        path: '/orders',
        summary: 'Neue Bestellung anlegen',
        requestBody: new OA\RequestBody(
            required: true,
            content: new OA\JsonContent(ref: new Model(type: CreateOrderRequest::class))
        ),
        responses: [
            new OA\Response(
                response: 201,
                description: 'Bestellung angelegt',
                content: new OA\JsonContent(ref: new Model(type: OrderResponse::class))
            ),
            new OA\Response(response: 400, description: 'Validierungsfehler'),
            new OA\Response(response: 401, description: 'Nicht authentifiziert'),
        ]
    )]
    public function create(CreateOrderRequest $request): JsonResponse
    {
        // Implementation...
        return $this->created($order);
    }
}

# Spec generieren:
# bin/console nelmio:apidoc:dump --format=yaml > openapi.yaml
# Oder über /api/doc.json direkt im Browser

3. OpenAPI-First: Stärken, Schwächen und wann er passt

Der entscheidende Vorteil von OpenAPI-First ist die Entkopplung von Design und Implementierung. Frontend-Teams können gegen einen Mock-Server entwickeln, der direkt aus der Spec generiert wird – noch bevor eine einzige Zeile Backend-Code existiert. Das eliminiert den häufigsten Engpass in der API-Entwicklung: das Warten auf den Backend-Entwickler. Teams können parallel arbeiten, und die API ist das explizit vereinbarte Vertragsdokument zwischen allen Beteiligten.

Ein weiterer Vorteil: Contract Testing wird trivial. Wenn die Spec die Quelle der Wahrheit ist, kann die Implementierung automatisch gegen die Spec validiert werden. Tools wie Dredd, Schemathesis oder openapi-contract-validator generieren Tests aus der Spec und prüfen ob die Implementation sie erfüllt – ohne manuell geschriebene Tests. Und jede Änderung an der API ist eine explizite, reviewbare Änderung an der Spec-Datei, nicht eine versteckte Änderung durch Refactoring.

Die Schwäche: Initialer Aufwand und YAML-Overhead. OpenAPI-First erfordert, dass das Team YAML schreiben kann und will. Für kleine Teams mit wenigen Konsumenten kann dieser Aufwand unverhältnismäßig sein. Und wenn die Spec und der Code nicht automatisch synchronisiert werden, entsteht Drift: Die Spec ist veraltet, die Implementation weicht ab, der Vertrag ist wertlos. OpenAPI-First ohne Drift-Detection ist schlimmer als Code-First ohne Spec.

4. Der Entscheidungsrahmen: Welcher Ansatz für welches Team?

Die Entscheidung zwischen OpenAPI-First und Code-First sollte auf fünf Faktoren basieren: Anzahl der API-Konsumenten (viele externe Konsumenten → OpenAPI-First), Parallelisierungsbedarf (Frontend und Backend parallel → OpenAPI-First), Team-Größe (kleines Team, schnelle Iteration → Code-First), API-Stabilität (häufige Breaking Changes → Code-First solange unstabil), und Governance-Anforderungen (formaler Change-Review-Prozess → OpenAPI-First).

Ein einfacher Entscheidungsbaum: Hat die API mehr als drei externe Konsumenten? → OpenAPI-First. Müssen Frontend und Backend parallel entwickeln? → OpenAPI-First. Ist die API noch im experimentellen Stadium mit häufigen Breaking Changes? → Code-First, aber mit Versionierung. Ist das Team kleiner als vier Backend-Entwickler und hat keine externen Konsumenten? → Code-First mit NelmioApiDoc. In allen anderen Fällen: OpenAPI-First.


# OpenAPI-First Workflow — Server-Stub-Generierung mit openapi-generator

# 1. Spec schreiben (openapi.yaml)
# 2. Server-Stubs generieren
# openapi-generator generate \
#   -i openapi.yaml \
#   -g php-symfony \
#   -o src/Generated \
#   --additional-properties=invokerPackage=App\\Generated

# 3. Interface implementieren (nicht überschreiben!)
# Generated: src/Generated/Api/OrdersApiInterface.php
# Implement: src/Api/OrdersApiImpl.php

# openapi-generator config (openapitools.json)
{
  "$schema": "https://openapi-generator.tech/schemas/config.json",
  "generatorName": "php-symfony",
  "inputSpec": "./openapi.yaml",
  "outputDir": "./src/Generated",
  "additionalProperties": {
    "invokerPackage": "App\\Generated",
    "apiPackage": "App\\Generated\\Api",
    "modelPackage": "App\\Generated\\Model",
    "phpLegacySupport": false,
    "composerPackageName": "mironsoft/api-generated"
  },
  "globalProperties": {
    "modelTests": "false",
    "apiTests": "false",
    "modelDocs": "false",
    "apiDocs": "false"
  }
}

# 4. Contract-Test gegen laufende API
# schemathesis run openapi.yaml --base-url=http://localhost:8080
# Testet automatisch alle Endpoints gegen die Spec

5. Tooling für Code-First in PHP/Symfony

Das Standard-Tool für Code-First in Symfony ist NelmioApiDocBundle, das OpenAPI-Specs aus PHP-Attributen (oder Annotations) generiert. Ab Version 4 werden OpenAPI 3.0 Specs generiert, Version 5 unterstützt OpenAPI 3.1. Das Bundle integriert sich mit Symfony Form Types, JMS Serializer und Symfony Serializer für automatische Schema-Generierung aus Request/Response-Klassen. Die generierte Spec kann als JSON über einen eingebauten Endpoint oder als YAML über den Console-Befehl exportiert werden.

Für bessere Code-First-Qualität lohnen sich zusätzliche Tools: Spectral als Linter der die generierte Spec gegen eigene Regeln prüft, openapi-diff der Breaking Changes zwischen Spec-Versionen erkennt und Dredd oder Schemathesis für Contract-Testing. Mit diesen drei Tools werden die größten Code-First-Schwächen adressiert: inkonsistentes Format (Spectral), versehentliche Breaking Changes (openapi-diff) und Drift zwischen Spec und Implementation (Contract Tests).

6. Tooling für OpenAPI-First

Der Standard-Stack für OpenAPI-First besteht aus vier Komponenten: Redocly CLI für Linting und Bundling der Spec-Dateien, openapi-generator für Client-SDK und Server-Stub-Generierung, einem Mock-Server (Prism von Stoplight oder openapi-mock) der aus der Spec generiert wird, und einem Contract-Test-Runner der die Implementierung gegen die Spec validiert.

Der OpenAPI-First Entwicklungs-Loop sieht konkret so aus: Designer/Architect schreibt oder aktualisiert die Spec. redocly lint prüft Syntax und Standards. Entwickler öffnen Pull Request. Automatischer Check in CI: Linting, Breaking-Change-Detection mit openapi-diff, und Contract-Tests gegen die aktuelle Staging-Umgebung. Nach Merge: openapi-generator generiert neue Client-SDKs und veröffentlicht sie in der internen Package-Registry. Mock-Server wird mit neuer Spec aktualisiert. Dieses Setup macht jeden Schritt automatisch und reviewbar.

7. Migration von Code-First zu OpenAPI-First

Teams die bereits Code-First entwickeln und zu OpenAPI-First wechseln wollen, können nicht einfach den Prozess umkehren. Die generierte Spec ist oft unvollständig, inkonsistent oder nicht ausreichend dokumentiert um als "Single Source of Truth" zu dienen. Der empfohlene Migrationspfad ist schrittweise: Zuerst die generierte Spec mit Spectral linten und die häufigsten Qualitätsprobleme beheben. Dann die Spec in eine separate Datei extrahieren und versionieren. Dann Contract-Tests einführen die sicherstellen, dass die Implementierung der Spec entspricht. Erst dann die Spec als autoritativen Prozess etablieren.

Der kritische Moment in der Migration: Der Übergang von "Spec als Dokumentation" zu "Spec als Vertrag". Das erfordert Disziplin: Änderungen an der API dürfen nur über Änderungen an der Spec beginnen, nicht durch direktes Code-Refactoring. Breaking Changes in der Spec werden reviewt und kommuniziert. Die CI-Pipeline verhindert, dass Code deployed wird, der nicht der Spec entspricht. Dieser kulturelle Wandel ist schwieriger als die technische Migration.

8. Direktvergleich der beiden Ansätze

Die folgende Tabelle fasst die wichtigsten Unterschiede zwischen OpenAPI-First und Code-First zusammen und gibt Empfehlungen für verschiedene Szenarien.

Kriterium Code-First OpenAPI-First Empfehlung
Entwicklungsgeschwindigkeit (initial) Schnell Langsamer (Spec-Overhead) Code-First für MVPs
Parallele Entwicklung (FE+BE) Nicht möglich Über Mock-Server OpenAPI-First ab 2+ Teams
Breaking-Change-Erkennung Manuell oder durch Tests Automatisch via openapi-diff OpenAPI-First mit externen APIs
Dokumentationsqualität Abhängig von Annotations Explizit und vollständig OpenAPI-First für Public APIs
Client-SDK-Generierung Möglich aber fragil Zuverlässig aus Spec OpenAPI-First für SDK-Publisher

9. Zusammenfassung

OpenAPI-First und Code-First sind keine absoluten Gegensätze, sondern Punkte auf einem Spektrum zwischen "maximale Flexibilität" und "maximale Kontrolle". Code-First gewinnt bei schnellen Iterationen, kleinen Teams und interner API-Nutzung. OpenAPI-First gewinnt bei externen Konsumenten, paralleler Frontend/Backend-Entwicklung, formalen Change-Prozessen und SDK-Veröffentlichung. Der Wechsel von Code-First zu OpenAPI-First ist eine kulturelle Migration, nicht nur eine technische – und sollte schrittweise mit klaren Meilensteinen umgesetzt werden.

Die pragmatische Empfehlung für die meisten Teams: Starte Code-First, solange die API intern und im Fluss ist. Wechsle zu OpenAPI-First, wenn die erste Version stabil ist und externe Konsumenten hinzukommen. Nutze in der Übergangsphase Spectral-Linting und Contract-Tests um die Qualität der generierten Spec zu sichern. Das gibt Entwicklungsgeschwindigkeit früh im Projekt und volle Kontrolle wenn die API geschäftskritisch wird.

OpenAPI-First vs. Code-First — Das Wichtigste auf einen Blick

Code-First wählen wenn...

API im experimentellen Stadium, kleines Team, interne Nutzung, schnelle Iteration wichtiger als Stabilität. NelmioApiDocBundle + Spectral als Linter.

OpenAPI-First wählen wenn...

Externe Konsumenten, parallele FE/BE-Entwicklung, SDK-Generierung, formale Change-Governance. Redocly CLI + openapi-generator + Mock-Server.

Migration

Schrittweise: erst Spec-Qualität mit Spectral verbessern, dann Contract-Tests einführen, dann Spec als autoritativen Prozess etablieren.

Entscheidungstest

Mehr als 3 externe Konsumenten? → OpenAPI-First. Frontend/Backend parallel? → OpenAPI-First. Sonst: Code-First solange agil, OpenAPI-First ab v1.

Mironsoft

API-Strategie, OpenAPI-Design und Entwicklungsprozess-Optimierung

API-Entwicklungsprozess optimieren?

Wir begleiten Teams beim Aufbau eines strukturierten API-Entwicklungsprozesses – von der Entscheidung OpenAPI-First vs. Code-First über Tooling-Setup bis zur CI-Integration mit Contract-Testing.

Prozess-Beratung

Welcher API-Workflow für euer Team und eure Konsumenten-Struktur

Tooling-Setup

Redocly, openapi-generator, Mock-Server und Contract-Tests einrichten

Migration

Von Code-First zu OpenAPI-First schrittweise migrieren

10. FAQ: OpenAPI-First vs. Code-First

1Hauptunterschied OpenAPI-First vs. Code-First?
Code-First: Implementation ist Quelle der Wahrheit. OpenAPI-First: Spec ist Quelle der Wahrheit. Entscheidet wer API-Design-Entscheidungen trifft: Entwickler spontan oder Architekten bewusst.
2Wann ist Code-First besser?
Interne APIs, kleine Teams, frühe Projektphasen mit häufigen Änderungen, kein externer Konsument. Entwicklungsgeschwindigkeit wichtiger als formale Kontrolle.
3Gute Dokumentation mit Code-First möglich?
Ja, mit vollständigen PHP-Attributen, Spectral-Linting und Contract-Tests. Aber der Mehraufwand übersteigt oft den initialen Aufwand für OpenAPI-First.
4Was ist Spec-Drift?
Spec und Implementation laufen auseinander. Verhindern: automatische Spec-Generierung (Code-First) oder Contract-Tests mit Schemathesis (OpenAPI-First). CI-Schritt bei Abweichung.
5Frontend ohne Backend entwickeln?
Mock-Server aus der Spec generieren: prism mock openapi.yaml. Antwortet auf alle definierten Endpoints mit Examples. Frontend kann voll entwickeln ohne laufendes Backend.
6Was ist Contract Testing?
Automatische Validierung ob eine API-Implementation ihrer Spec entspricht. Schemathesis generiert Requests aus der Spec und prüft Responses. Kein manuelles Schreiben nötig.
7Code-First Tool für Symfony?
NelmioApiDocBundle (v4 für 3.0, v5 für 3.1) + Spectral-Linting + openapi-diff für Breaking Changes + Schemathesis für Contract-Tests.
8OpenAPI-First Tool-Stack?
Redocly CLI + openapi-generator + Prism Mock-Server + Schemathesis. Stoplight Studio als GUI-Editor für nicht-technische Stakeholder.
9Dauer der Migration?
2-4 Wochen technisch für 20-30 Endpoints. Kultureller Wandel (Spec als autoritativer Prozess) dauert 1-2 Monate zusätzlich.
10Hybride Ansätze möglich?
Ja, neue Endpoints OpenAPI-First, bestehende Code-First belassen und schrittweise migrieren. Aber ein einheitlicher Prozess ist langfristig wartbarer als dauerhafter Mischbetrieb.