APIを作る際のAPIバージョンに関するメモ

はじめに


APIを作るときにどうするか?を開発チーム内で議論したので、備忘録的なメモ

発端となった会話は、こんな感じだったはず

「マイクロアーキテクチャなサービスを作ったときってAPIを作ると思うけど、ライフサイクルって考えてる?」
「APIを利用するフロントは更新できるけど、APIは依存されるものが多いから簡単には更新できないよね?」
「APIってモバイルアプリからも利用した場合、修正しづらくない?バージョン管理でもするの?」

APIの種別


以下の3つぐらいになりそう

  • 外部公開向け
  • モバイルアプリ向け
  • webサービス向け

外部公開向け


  • API変更の影響が大きい
  • ドキュメント更新必須
  • 利用者が離れるのでドラスティックな変更はできない
  • 利用者への周知が必須

モバイルアプリ向け


  • アプリのみが影響を受けるので、API変更における影響は少ない
  • アプリバージョンによるので自由にAPI更新ができない
  • OSバージョンによってアプリのアップデートができないことが多いので、更新によって使えなくなる可能性有
  • 更新API対応のアプリであっても、アプリが更新されることは無いと思ったほうがよい

webサービス向け


  • クライアントもAPIに合わせて最新にできるので、変更しやすい
  • キャッシュされたクライアントのコードとのデータ不整合が起きやすい
  • キャッシュに振り回される(iOSのwebview等)

バージョニング方式


APIのバージョン管理方式は以下のものが採用される傾向にある

  1. アクセス先URIそのものを大きく変更する
  2. URIにバージョンを埋め込む
  3. クエリに使用APIバージョンを入れる
  4. メディアタイプにバージョンを指定する

世間的には、2のパターンが比較的多く採用される傾向

URIにバージョンを埋め込み方式


  • 「v1」のように「v」をつけてバージョンを明確にすることが多い
  • 日付やリリースバージョン(ハッシュ等)をバージョンにするAPIもある(twillo等)
  • URIに組み込むバージョンは、メジャー番号のみを含める
  • APIの修正は、後方互換を保ちつつ対応する

バージョニングは以下のセマンティックバージョニング方式を取ることが多い

  • パッチバージョンは、ソフトウェアのAPIに変更がないバグ修正を行ったときに増える
  • マイナーバージョンは後方互換がある機能変更、特定の機能追加のときに増える
  • メジャーバージョンは後方互換が無い変更の時に増える

メディアタイプにバージョンを指定する


  • 「Accept: application/vnd.example.v2+json」のような形で規定する
  • URIがリソースを表しているので、HTTPの文法に則っている
  • 「Content-Type」の指定誤りで、サーバ、クライアント側ともにエラーになりやすい傾向

バージョン変更指針


  • APIは基本変更しないほうがよい
  • 変更は後方互換を保ちつつ対応できる場合は、マイナーバージョンアップ(可能な限りこちらを選択)
  • 後方互換が保てない修正の場合はメジャーバージョンアップ
  • レスポンスデータ整合性/整理のためであれば、バージョンは上げない(後方互換を維持し続け、ドキュメント整理で対応)

メジャーバージョンアップ指針


後方互換が保てない場合のみ実施し、バージョンアップのルールを整理してから行う

  • セキュリティ/権限などのAPI使用ルール変更
  • 認証方式の変更
  • 乱雑に作った(ルールが無い)APIを使いやすくするための整備

APIの提供終了


  • API提供終了前に提供終了日時のアナウンスをする(提供終了後、半年ほどは動かしておくこと)
  • 提供終了までにAPIを利用できなくするブラックアウトテストを数回実施する
  • API提供終了の仕様をドキュメントに盛り込んでおく(HTTPのステータスコード410(Gone)を返すなど)
  • 利用期限をAPI提供開始時に決めておく
  • 古いAPIを叩いたときに、新APIへのリダイレクトは、混乱を招くので避けたほうがよい

# モバイル向けAPIの場合、ユーザー体験に直結するので仕様として予め考えておく(モバイル向けの場合、APIの停止はトレンドを見つつ行うこと) # アプリのアップデートを促すようにしておく(強制アップデートは好まれないが、使えなくなるよりも遥かにマシ)