REST-Web-Service-Versionierung in der Praxis

8

Ich erstelle einen neuen Webdienst und habe einige der E-Books von APIgee gelesen, in denen die Versionierung des Webdienstes empfohlen wird. Ich verstehe, dass es einen "Kampf" zwischen der Speicherung von Versionsinformationen in der URL und dem Header gibt. Von dem, was ich gelesen und verstanden habe, möchte ich Versionierung in der Kopfzeile verwenden.

Meine Frage ist; Wie sieht das in der Praxis aus? Ich benutze Spring MVC 3.2. Erstellen Sie einfach solche Methoden in demselben Controller, der auf verschiedene Versionen reagiert?

Version 1:

%Vor%

Version 2:

%Vor%

Oder ist das falsch? Oder ist es üblicher, verschiedene Pakete zu erstellen, die verschiedene Versionen des Controllers enthalten? Oder gibt es andere Wege?

    
LuckyLuke 21.09.2013, 18:45
quelle

1 Antwort

19

Das Problem hier ist weniger, wo die Versionsinformation lebt (URI vs Header) und mehr darüber, wie Sie Code für verschiedene Versionen organisieren.

Ich bezweifle, dass es einen einheitlichen Standardansatz gibt. Es hängt nur davon ab, wie unterschiedlich die Versionen sind.

Einfache Formatänderung. Nehmen Sie zum Beispiel an, dass der einzige Unterschied darin besteht, dass Sie von XML in V1 zu JSON in V2 gewechselt sind. In diesem Fall könnten Sie genau den gleichen Code verwenden, aber konfigurieren Sie die App stattdessen so, dass sie JSON global ausgibt. Keine Notwendigkeit für verschiedene Pakete oder Controller. (Sie können beispielsweise JAXB-Anmerkungen verwenden, um sowohl die von XML als auch von Jackson generierte JSON-Ausgabe zu steuern.)

Modest-Schema-Änderungen. Sagen Sie, dass V2 eine kleine Anzahl von brechenden Schemaänderungen einführt. In diesem Fall wäre es wahrscheinlich nicht sinnvoll, neue Pakete darüber zu erstellen. Sie könnten einfach nur bedingte Logik in Ihrem Controller haben, um die richtige Darstellung für die Version zu verarbeiten / zu bedienen.

Wichtige Schemaänderungen. Wenn Ihre Schemaänderungen tief und weitreichend sind, benötigen Sie möglicherweise mehr als separate Controller. Möglicherweise benötigen Sie sogar ein anderes Domänenmodell (Entitäten / Dienste). In diesem Fall kann es sinnvoll sein, einen parallelen Paketsatz für Controller bis hin zu Entitäten, Repos und möglicherweise sogar Datenbanktabellen zu haben.

Anwendung der Ideen

Approach 1. Wenn Sie diese Ideen auf Ihre @RequestMapping -Beispiele anwenden, können Sie das tun, was Sie dort sagen. Wenn die Antwort zwischen den Versionen jedoch genau gleich ist, sollten sie nur an eine einzige Freigabe delegieren Methode:

%Vor%

So etwas würde funktionieren. Wenn die Aufträge zwischen den Versionen unterschiedlich sind, können Sie die Unterschiede direkt in der Methode implementieren.

Ansatz 2 Eine andere Sache, die Sie versuchen könnten - und ich habe es selbst nicht versucht - ist, dass jeder Ressourcentyp (zB Bestellungen, Produkte, Kunden usw.) seine eigene Basis hat Controller mit Annotationen auf Methodenebene für die HTTP-Methode (nur value und method definiert, aber nicht produces ). Verwenden Sie dann versionsspezifische Erweiterungen, die die Basis erweitern, wobei die Erweiterungscontroller das @RequestMapping(value = "/orders", produces = "application/vnd.example-v1") auf Klassenebene haben. Überschreiben Sie dann nur Deltas zwischen der Version und der Baseline. Ich bin mir nicht sicher, ob das funktioniert , aber wenn es so wäre, wäre es eine ziemlich saubere Art, Controller zu organisieren. Hier ist, was ich meine:

%Vor%     
Willie Wheeler 21.09.2013, 19:21
quelle

Tags und Links