Wersjonowanie API
Jak zmieniać API bez zrywania klientów — URL path, header, date-based jak Stripe, Sunset header, Pact contract testing i openapi-diff.
6 strategii wersjonowania API
Każde podejście ma kompromisy między czystością URL, cacheowaniem, testowalnoscia i RESTfulness.
| Strategia | Widoczność | Cache CDN | Testowanie | RESTfulness | Kto używa |
|---|---|---|---|---|---|
| URL Path (/v1/users) | W URL | Doskonały (URL = key) | Proste (curl/browser) | Nieidealne | Stripe, Twilio, GitHub REST, AWS |
| Header (X-API-Version) | Ukryta | Wymaga Vary header | Wymaga narzędzi | Poprawne | GitHub API v4, wewnętrzne API |
| Query Param (?v=2) | W URL | Dobry | Proste | Akceptowalne | YouTube API, Google Maps |
| Date-based (YYYY-MM-DD) | W headerze | Wymaga Vary header | Wymaga narzędzi | Poprawne | Stripe, GitHub (nowy) |
| Content Negotiation | W Accept header | Wymaga Vary header | Skomplikowane | Idealne (RFC) | GitHub v3 (Accept header) |
| GraphQL @deprecated | W schemacie | Per query hash | Proste | N/A (GraphQL) | Wszystkie GraphQL API |
Często zadawane pytania
Co to jest wersjonowanie API i dlaczego jest ważne?
Wersjonowanie API to sposób zarządzania zmianami interfejsu programistycznego bez zrywania kompatybilności z istniejącymi klientami. Problem bez wersjonowania: zmiana struktury odpowiedzi API zrywa wszystkich klientów którzy jej używają. Typy zmian: Non-breaking (backward compatible) — dodanie nowego opcjonalnego pola, nowego endpointu, nowej wartości enum. Klienci mogą ignorować nowe pola. Breaking — usunięcie pola, zmiana typu danych, zmiana nazwy pola, zmiana semantyki. Wymaga nowej wersji API. Strategie wersjonowania: URL versioning (/v1/users, /v2/users) — najprostsze, widoczne w URL, łatwe do testowania. Header versioning (Accept: application/vnd.api+json;version=2) — czystszy URL, trudniej przetestować w przeglądarce. Query parameter (?version=2 lub ?v=2) — prosta implementacja, ale brzydki URL. Content-type versioning (application/vnd.myapp.v2+json) — RESTful, ale skomplikowane. Sufix versioning dla zasobów (Accept: application/vnd.myapp.user.v2+json) — granularne, ale bardzo skomplikowane. Rekomendacja w 2024: URL versioning (/v1/, /v2/) dla publicznych API, header versioning dla wewnętrznych.
Jak deprecować wersję API bez zrywania klientów?
Deprecation strategy: zapowiedź z wyprzedzeniem. Sunset Header (RFC 8594): Sunset: Sat, 31 Dec 2025 23:59:59 GMT — informuje kiedy wersja zostanie wyłączona. Deprecation: true — informuje że wersja jest deprecated. Link: rel='successor-version' — wskazuje nową wersję. Komunikacja: email do wszystkich znanych konsumentów API. Changelog z datą EOL. Dokumentacja z migration guide. Monitoring: śledzenie kto nadal używa starej wersji. Dashboard usage per version. Alerty gdy klient nie migruje do deadline. Versioning dla REST vs GraphQL: REST — wersjonowanie całego API lub per endpoint. GraphQL — @deprecated na polach i typach, nie ma URL versioning. GraphQL Federation — subgraph versioning. API Gateway: Kong/AWS API Gateway/Traefik — routing per wersja. Canary routing — 5% ruchu na v2 dla testów. Blue/Green dla wersji API. Semantic versioning dla SDK klientów: major.minor.patch. Major — breaking change. Minor — nowe funkcje backward-compatible. Patch — bugfix.
URL versioning vs Header versioning — co wybrać?
URL versioning (/v1/users): Zalety — widoczny w URL, łatwy do cachowania przez CDN (URL = cache key), prosty do testowania (curl, Postman, przeglądarka), zrozumiały dla deweloperów, łatwe routing w API gateway. Wady — nie jest 'puryście RESTful' (URL powinien identyfikować zasób, nie wersję API), URL zmienia się przy każdej wersji. Header versioning (Accept: application/vnd.api.v2+json lub custom X-API-Version: 2): Zalety — czystszy URL, URL identyfikuje zasób, jeden URL na zawsze. Wady — trudniejszy do testowania (browser nie może łatwo ustawić nagłówka), problemy z cacheowaniem CDN (różne odpowiedzi dla tego samego URL), wymaga Vary: X-API-Version header dla poprawnego cache. Query parameter (?v=2): Zalety — prosta implementacja, widoczna w URL. Wady — brzydki URL, łatwo pominąć, niekonwencjonalne. Rekomendacje po platformach: Stripe — URL versioning + date versioning (2023-10-16). Twilio — URL versioning (/v1/, /v2/). GitHub API — header versioning (X-GitHub-Api-Version). Google APIs — URL versioning (/v1/, /v2/). AWS — URL versioning + date versioning. PayPal — URL versioning. Wniosek: dla nowych public API publicznych — URL versioning. Dla wewnętrznych API — co team preferuje.
Date-based versioning API — strategia Stripe?
Stripe date versioning: zamiast v1/v2 używa dat wersji. Każdy request ma nagłówek Stripe-Version: 2023-10-16. Domyślna wersja = wersja z dnia rejestracji konta. Changelog per data — każda zmiana ma datę. Klient może upgrade'ować wersję w swoim dashboardzie. Zalety date versioning: granularne — nie musisz upgrade'ować całego API. Jasna historia zmian. Klient kontroluje kiedy migratuje. Wady: złożona implementacja — musisz transformować dane między wersjami. N wersji do utrzymania jednocześnie. Implementacja: middleware transformuje request/response. Per-endpoint versioning map. Feature flag per wersja. Podobne podejście: GitHub (X-GitHub-Api-Version: 2022-11-28). Salesforce (wersje po datach). Twilio (daty jako wersje). API versioning w Kubernetes: Kubernetes ma własny model — alpha (v1alpha1), beta (v1beta1), stable (v1). Migracja: v1alpha1 -> v1beta1 -> v1. Kubectl apply obsługuje konwersję między wersjami. API versioning w GraphQL: GraphQL nie ma standardowego versioning — używa @deprecated, additive changes. Gdy breaking change — nowy typ/pole z prefixem lub postfixem v2. Unikaj breaking changes w GraphQL przez design.
API contract testing — jak testować kompatybilność między wersjami?
Contract testing: zamiast integracyjnych testów end-to-end — testuj kontrakt (umowę) między consumer i provider. Pact: najpopularniejszy framework contract testing. Consumer pisze test — definiuje co oczekuje od API. Pact generuje contract file (pact). Provider weryfikuje contract — czy spełnia wszystkie expectations. Pact Broker: centralny rejestr kontraktów. Webhook — powiadom provider gdy consumer zmienił kontrakt. Can I Deploy: sprawdź czy możesz bezpiecznie deploy. Prism (Stoplight): mock server z OpenAPI spec. Validate requests i responses vs spec. Contract testing dla eventów: Pact dla message-based (Kafka, RabbitMQ). Consumer definiuje oczekiwany message format. OpenAPI/AsyncAPI: OpenAPI 3.x — specyfikacja REST API. AsyncAPI — specyfikacja event-driven API (WebSocket, Kafka, AMQP). Spectral: linter dla OpenAPI/AsyncAPI. Enforce naming conventions, security headers, pagination. Backward compatibility checking: openapi-diff — porównuje dwie wersje OpenAPI spec. breaking-change-detector. oasdiff. Integracja z CI: blokuj PR jeśli zmiana jest breaking. Automatyczny changelog z diff. Versioning w mikrousługach: każdy serwis wersjonuje swoje API niezależnie. Service mesh — routing per wersja. Canary testing nowych wersji API.
Powiązane artykuły
Skontaktuj się z nami
Porozmawiajmy o Twoim projekcie. Bezpłatna wycena w ciągu 24 godzin.
Wyślij zapytanie
Telefon
+48 790 814 814
Pon-Pt: 9:00 - 18:00
adam@fotz.pl
Odpowiadamy w ciągu 24h
Adres
Plac Wolności 16
61-739 Poznań
Godziny pracy
Wolisz porozmawiać?
Zadzwoń teraz i porozmawiaj z naszym specjalistą o Twoim projekcie.
Zadzwoń teraz