Jak wykonać prawidłowo wersjonowanie API? Odpowiemy sobie na to pytanie analizując produkty (Twitter, Facebook, YouTube, Google Maps, GitHub, GitLab, Azure) największych graczy na rynku. Wyobraźmy sobie sytuacje nadchodzi dzień, w którym biznes podaje nowe wymaganie, wiąże się to z zmianą modelu przekazywanego do żądania. Zmiana modelu w aktualnym kodzie spowoduje, że klient nie otrzyma prawidłowej odpowiedzi dla wysłanych żądań. Trzeba mieć na uwadze, że klienci mogą nie chcieć aktualizować swoich aplikacji po zmianie interfejsu API. Natomiast w przypadku klientów mobilnych, nie zawsze można łatwo wymusić aktualizację aplikacji mobilnej na urządzeniu użytkownika. Aktualizacja umowy API jest wyzwaniem, które można sprostać stosując wersjonowanie API. Implementując wersjonowanie umożliwiamy użytkownikowi korzystanie z istniejącego interfejsu API, bez potrzeby natychmiastowej migracji do nowej wersji. W powyższym artykule omówię cztery popularne sposoby na wersjonowanie API:
- Path URI,
- Parameter URI,
- Custom header,
- Accept header.
Wersjonowanie API za pomocą ścieżki URI
To podejście jest najpopularniejszą metodą używaną przez interfejsy API, polega na dodaniu nowego numeru wersji do adresu URL.
http://www.example.com/api/{version_number}/users http://www.example.com/api/v_{version_number}/users http://www.example.com/api/v{version_number}/users
Powyższe rozwiązanie stosuje np. Twitter w swoim Twitter Ads API, Facebook, YouTube, GitLab etc.
https://www.googleapis.com/youtube/v3
Zaletą jest prostota w użyciu i testowaniu. Wadą powyższego rozwiązanie jest udostępnienie zasobu pod wieloma adresami URL. Dodając numer wersji do adresu łamiemy zasady stojące za założeniami architektury REST, numer wersji nie stanowi elementu ścieżki identyfikującej zasób.
Wersjonowanie przez parametr URI
Drugim sposobem wersjonowania API jest podanie numeru wersji, jako parametr żądania.
http://www.example.com/api/users?version={version_number} http://www.example.com/api/users?v={version_number}
Zaletą powyższego rozwiązania jest możliwość ustawienia domyślnie najnowszej wersji API w przypadku, gdy parametr zapytania określający wersje nie został podany. Za wadę można uznać trudność routingu w porównaniu do pierwszej wersji. Negatywnie możemy także ocenić mieszanie parametrów metody z parametrem wersji.
https://maps.googleapis.com/maps/api/js?v=3.33&key=YOUR_API_KEY&callback=initMap
Powyższe rozwiązanie wykorzystywane jest głównie w JavaScript API np. w Google Maps.
Wersjonowanie przez Custom header
Trzecią omawianą strategią wersjonowania jest wykorzystanie niestandardowego nagłówku, czyli nagłówku nieznajdującego się w specyfikacji HTTP. W nagłówku przesyłamy informacje o wersji API.
Request Headers: x-ms-version: 2017-07-29
Powyższe rozwiązanie używane jest przez Microsoft w Azure Storage Services. O wadach i zaletach powyższej strategii opowiem dopiero po analizie kolejnego podejścia (Accept header).
Wersjonowanie przez Accept header
W podejściu numer cztery do wersjonowania API wykorzystujemy standardowy nagłówek Accept. Powyższe rozwiązania w swoim REST API wykorzystuje znany wszystkim programistom GitHub.
Accept: application/vnd.github.v3+json
GitHub dla przypadku gdy nie zostanie podany numer wersji w nagłówku Accept udostępni domyślnie najnowszą wersje API, które z upływem czasu może ulec zmianie.
application/vnd.github+json
Tym samym GitHub zaleca zawsze podawać konkretną wersje nagłówka Accept, by uniknąć problemu z zmianą domyślnej wersji API. W odpowiedzi na żądanie w nagłówku X-GitHub-Media-Type uzyskujemy informacje o wersji API.
Stosując nagłówki w porównaniu do pierwszych dwóch strategii nie powodujemy przekazywania informacji o numerze wersji w URI. Tym samym każdy zasób jest identyfikowany przez jeden adres. Unikamy także mieszania parametrów takich jak wersja z parametrami biznesowymi aplikacji. To podejście jest najbliżej prawidłowej implementacji architektury REST. Rozwiązanie z nagłówkami jest trudniejsze w testowaniu, w adresie URL nie jest wyświetlany numer wersji, a użytkownik musi znać przeznaczenie nagłówków.
Podsumowanie
Powyższe strategie wersjonowania mają swoich przeciwników jak i zwolenników. Nie zależnie od wybranej metody, stosując wersjonowanie zapewniamy lepsze API. Każdego tygodnia, miesiąca, roku możemy wprowadzać/usuwać/modyfikować funkcje w udostępnianym API bez obawy przed złamaniem kontraktu w aplikacji klienckiej użytkownika. Nowa wersja API powinna być za każdym razem wydawana, jeśli wprowadzone zmiany łamią aktualną umowę API. Jeśli zastanawiasz się jak długo powinieneś wspierać starsze wersje API, tutaj wszystko zależy od polityki firmy (może być to 6 miesięcy, 2 lata etc.).