API-Änderungen

API-Versionierung: Best Practices im Sinne der Aufrufer

7 Min. Lesezeit

API-Versionierung ist die Praxis, einen alten Vertrag nach einer Änderung weiterlaufen zu lassen, damit Aufrufer nach ihrem eigenen Zeitplan umziehen können statt nach eurem. Dieser Satz enthält die beiden Entscheidungen, die zählen: Was zählt als Vertragsänderung, und wie lange läuft die alte Version weiter. Wo die Versionsnummer lebt, worüber sich die meisten Versionierungsdebatten drehen, ist die unwichtigste der drei und die am leichtesten richtig zu machende.

Wann sollte man eine API versionieren?

Versioniert eine API nur, wenn eine Änderung einen korrekten Aufrufer brechen würde. Additive Änderungen, neue Felder, neue Endpunkte, neue optionale Parameter, brauchen keine Version; gegen den alten Vertrag geschriebene Aufrufer funktionieren weiter, und die neue Fähigkeit ist einfach da. Ein Breaking Change braucht eine, weil die Alternative ist, dass ein Aufrufer es von einem Fehler erfährt. Jedes Release zu versionieren, auch die additiven, bringt Aufrufern bei, dass Versionen Rauschen sind, und sie hören auf, die Hinweise zu lesen, die zählen.

Der praktische Test ist derselbe wie im Artikel über Breaking Changes: Muss ein Aufrufer, der sich nur auf dokumentiertes Verhalten verlassen hat, etwas ändern, um weiter zu funktionieren, braucht die Änderung eine Version. Wenn nicht, liefert sie unter der aktuellen Version aus und schreibt einen Changelog-Eintrag.

Welches API-Versionierungsschema sollte man nutzen?

Nutzt das Schema, das eure Aufrufer am leichtesten sehen und setzen können, was für die meisten öffentlichen APIs eine Version im URL-Pfad oder ein datierter Versions-Header ist. Die vier üblichen Schemata unterscheiden sich weniger in ihren Fähigkeiten als darin, was sie vom Aufrufer verlangen, und das ist die richtige Grundlage für die Wahl.

SchemaBeispielWas der Aufrufer tun mussWer es nutzt
URL-Pfad/v2/invoicesDie URL bei der Migration ändernDie meisten öffentlichen REST-APIs
Versions-HeaderX-GitHub-Api-Version: 2022-11-28Einen Header senden, oder den Standard akzeptierenGitHub
Datierte Konto-VersionStripe-Version: 2026-08-26Ein Datum pro Anfrage oder pro Konto festlegenStripe
Query-Parameter/invoices?version=2Einen Parameter anhängenÄltere APIs; heute selten gewählt
Media-TypeAccept: application/vnd.example.v2+jsonContent-Typen aushandelnPuristen; wenige Aufrufer beherrschen es

URL-Pfad ist am sichtbarsten und am wenigsten flexibel. Jeder Aufrufer kann seine Version an einer Log-Zeile ablesen, und ein Versionssprung ist ein Suchen-und-Ersetzen. Der Preis: Die ganze Oberfläche bewegt sich auf einmal, man kann nicht den Vertrag eines einzelnen Endpunkts ändern, ohne für alle eine neue Version zu prägen, weshalb Pfadversionen selten und groß bleiben.

Versions-Header hält URLs stabil und lässt den Server einen Standard für Aufrufer wählen, die nichts senden, so wie GitHubs REST-API-Versionierung funktioniert: eine datumsbenannte Version in X-GitHub-Api-Version, mit der ältesten unterstützten Version als Standard, damit unversionierte Aufrufer nicht brechen. Der Preis: Die Version ist in einer URL unsichtbar und in einem neuen Client leicht zu vergessen.

Datierte Konto-Version ist das Header-Schema plus einer Ergänzung: Die Version wird beim Konto gespeichert, sodass jede Anfrage sie bekommt, ohne etwas zu senden. Stripes API-Versionierung bindet jedes Konto an die Version, mit der es angelegt wurde, und lässt eine Anfrage das mit Stripe-Version überschreiben. Das ist das aufruferfreundlichste Schema und die meiste Arbeit im Betrieb, weil der Server zwischen jeder unterstützten Version und der aktuellen übersetzen muss.

Query-Parameter und Media-Type funktionieren beide und scheitern beide auf verschiedene Art am Sichtbarkeitstest: ein Query-Parameter fällt beim Bauen einer URL leicht weg, und eine Media-Type-Version ist für fast jedes Werkzeug unsichtbar, mit dem ein Aufrufer debuggt. Stripes datumsbasiertes Schema ist das bekannteste Beispiel für den Datumsansatz, und wie Stripe seine API versioniert geht es durch.

Wie läuft API-Versionierung in der Praxis ab?

In der Praxis ist eine Version eine benannte Menge von Verhaltensweisen, und der Server bildet jede Anfrage auf eine davon ab. Die Schritte sind gleich, egal welches Schema den Namen trägt.

  1. Benennt Versionen nach Datum oder Ganzzahl, nicht nach semantischer Version. Eine Web-API ist kein Paket. Aufrufer können keine Minor-Version einer URL pinnen, also sagt v2 oder 2026-08-26 alles, was ein Aufrufer braucht, und semantische Versionierung impliziert ein Kompatibilitätsversprechen, das das Schema nicht einlösen kann.
  2. Haltet die Version aus dem Code fern, der sie nicht braucht. Eine Version sollte an der Kante eine Übersetzungsschicht auswählen, nicht die Geschäftslogik verzweigen. Zwei vollständige Kopien der Codebasis sind, wie eine Version unwartbar wird.
  3. Gebt jeder Version einen Standard und ein Dokument. Aufrufer, die keine Version senden, bekommen die älteste unterstützte, nie die neueste, damit ein ungepinnter Client nicht am Release-Tag bricht. Jede Version hat eine Seite, die sagt, was sich zur vorherigen geändert hat.
  4. Setzt ein Support-Fenster und veröffentlicht es. Googles Versionierungsleitfaden AIP-185 verlangt eine angemessene, gut kommunizierte Übergangsfrist und empfiehlt 180 Tage sogar für Beta-Funktionen. Wählt ein Fenster, schreibt es auf, und wendet es an, ohne pro Version neu zu verhandeln.
  5. Zieht Versionen zurück wie Endpunkte. Eine Version nach ihrem Fenster bekommt dieselbe Behandlung wie jede abgekündigte API: eine Ankündigung, ein Sunset-Header (RFC 8594) auf jeder Antwort, eine Erinnerung auf halber Strecke an die verbliebenen Aufrufer, und ein Entfernungsdatum, das hält.

Was sind v1 und v2 in einer REST-API?

v1 und v2 sind Namen für zwei Verträge, die derselbe Server gleichzeitig unterstützt. Ein v2 existiert, weil etwas in v1 nicht geändert werden konnte, ohne dessen Aufrufer zu brechen, also ging die Änderung in einen neuen Vertrag, und der alte lief weiter. Die Zahlen implizieren nicht, dass v2 vollständig oder v1 tot ist; beides stimmt nur, wenn die Dokumentation es sagt. Ein v3, das jedes Quartal erscheint, ist ein Zeichen, dass additive Änderungen versioniert werden, oder dass der Vertrag nie darauf ausgelegt war, Änderungen aufzunehmen. gRPC löst dasselbe Problem anders: gRPC und Protobuf API-Änderungen behandelt Versionierung über den Paketnamen in einer .proto-Datei statt einen URL-Pfad, und ein Wire-Format, in dem ein Feld umzubenennen kostenlos ist, aber eines umzunummerieren ein Breaking Change, den kein REST-Aufrufer als riskant erkennen würde.

Was sollte eine Versionsänderung ankündigen?

Eine Versionsänderung sollte ankündigen, was bricht, wen es betrifft, wie man migriert, und wie lange die vorherige Version weiterläuft. Der Eintrag hat dieselbe Form wie jeder andere Breaking-Change-Eintrag, plus eine Zeile mit dem Support-Fenster. Hier einer für eine header-versionierte API:

API-Version 2026-11-01 ist verfügbar. Version 2025-06-15 wird bis 1. November 2027 unterstützt. Neu in 2026-11-01: GET /invoices gibt amount in kleinsten Einheiten als Ganzzahl statt als Dezimal-String zurück, und das abgekündigte Feld customer_name entfällt zugunsten des customer-Objekts. Betrifft Aufrufer auf 2025-06-15, die amount als String parsen, was der Standard für ungepinnte, vor Juni 2025 angelegte Clients ist. Migration: amount als Ganzzahl parsen und den Namen aus customer.name lesen. X-Api-Version: 2026-11-01 pinnen, wenn bereit. Für Aufrufer ohne Pinning ändert sich nichts.

Der letzte Satz ist der, bei dem die meisten Leserinnen aufhören können zu lesen, und er gehört in jede Versionsankündigung. Die Seite Changelog-Beispiele enthält Einträge von APIs, die so versionieren, und der Unterschied zwischen den guten und dem Rest liegt meist genau in diesem letzten Satz.

Wer wird informiert, wenn sich eine Version ändert?

Jeder auf der alten Version, einzeln, und der Changelog für alle anderen. Eine Versionsänderung ist der eine Fall, in dem “wir haben darüber gepostet” garantiert genau die Aufrufer verfehlt, die zählen: die, die vor zwei Jahren eine Version gepinnt und seither keine Release Notes mehr gelesen haben. Nutzungsdaten beantworten, wer sie sind; die Benachrichtigung muss sie dort erreichen, wo ihr Code ist, in den Response-Headern und in einer Nachricht an die Kontoinhaberin.

In unserem Loop wird der Eintrag, der eine Version ankündigt, aus dem Pull Request entworfen, der sie ausliefert, von einem Menschen geprüft, und im Feed und Widget veröffentlicht, wo ein versionierter Client ihn als JSON lesen kann. Wessen Widget-Feedback um die Änderung gebeten oder den Bug gemeldet hat, den sie behebt, und zu einem GitHub-Issue wurde, das der Pull Request schließt, wird auf diesem Issue informiert, sobald der Eintrag live geht. Der Mechanismus ist derselbe wie bei jedem Eintrag; ein Versionssprung ist nur der Eintrag mit dem höchsten Einsatz.

FAQ

Sollte jede API-Änderung eine neue Version bekommen? Nein. Nur Breaking Changes. Additive Änderungen liefern unter der aktuellen Version mit einem Changelog-Eintrag aus. Additive Änderungen zu versionieren trainiert Aufrufer, Versionen zu ignorieren.

Ist URL-Versionierung oder Header-Versionierung besser? URL-Versionierung ist für Aufrufer leichter zu sehen und für euch schwerer stückweise weiterzuentwickeln; Header-Versionierung ist umgekehrt. Für eine öffentliche API mit vielen kleinen Clients scheitert URL-Versionierung seltener. Für eine große API mit Übersetzungsschicht skaliert die datierte Header-Version besser.

Wie viele Versionen sollten gleichzeitig unterstützt werden? So wenige, wie das Support-Fenster erlaubt, und nie eine unbegrenzte Zahl. Zwei oder drei parallele Versionen sind normal; mehr bedeutet meist, dass Versionen nicht zurückgezogen werden.

Was sollten unversionierte Anfragen bekommen? Die älteste unterstützte Version, damit bestehende ungepinnte Clients weiterlaufen, mit einem Response-Header, der ihnen sagt, welche Version sie erhalten haben.


Die technischen Aussagen in diesem Artikel wurden nicht unabhängig geprüft. Wenn etwas nicht stimmt, sagen Sie es uns, und wir korrigieren es.

Mehr bei changeloop: Entwicklerdokumentation, Changelog-Beispiele

changeloop
Das Team hinter einem Changelog, das den Kreis schließt. Ihre Nutzer fragen, Ihr Team liefert, und wer gefragt hat, erfährt davon.