💡 Key Takeaways
- Principle 1: Design Your API Like a Product, Not a Database Wrapper
- Principle 2: Embrace HTTP Status Codes Properly (But Don't Overthink Them)
- Principle 3: Version Your API From Day One (And Do It Right)
- Principle 4: Design Intuitive Resource Naming and URL Structures
私は今でも、私たちのCEOに私たちのモバイルアプリがユーザーのデータプランを森林火災のように燃やしている理由を説明しなければならなかった日を覚えています。それは2016年で、私はフィンテックスタートアップのリードAPIアーキテクトとして3年目でした。私たちのREST APIは、アプリが口座残高を確認するたびに、プロフィール写真をbase64でエンコードした完全なユーザーオブジェクトを返していました。私たちは顧客を失い続けており、私が設計したAPIが私たちを殺していたのです。
💡 主なポイント
- 原則 1: APIを製品のように設計する、データベースラッパーのようにしない
- 原則 2: HTTPステータスコードを適切に使用する(しかし、考えすぎない)
- 原則 3: APIを初日からバージョン管理する(そして、正しく行う)
- 原則 4: 直感的なリソース名付けとURL構造を設計する
その痛ましい教訓は、私に重要なことを教えてくれました:REST API設計は、単に物事を機能させることだけではありません。それは、テキストブックが決して言及しない実世界の条件下で、物事をうまく機能させることです。この12年間、10人のスタートアップからFortune 500の企業まで、さまざまな会社のためにAPIを構築してきた中で、同じ間違いが繰り返されるのを見てきました。そして、私自身もほとんどの間違いを犯しました。
今日は、私がAPI設計を変革した10の原則を共有します。これらは、学術論文からの理論的な概念ではありません。それらは、1日に何百万ものリクエストを処理する本番環境で鍛えられた実戦経験に基づくガイドラインです。初めてAPIを構築している場合でも、10回目のAPIを再構築している場合でも、これらの原則は開発者が実際に使用したいインターフェースを作成するのに役立ちます。
原則 1: APIを製品のように設計する、データベースラッパーのようにしない
REST API設計において私が見ている最大の間違いは、APIをデータベーステーブルの薄い層として扱うことです。私は、エンドポイントがデータベーススキーマと1対1でマッピングされ、内部実装の詳細をさらけ出すようなAPIを数百件レビューしてきました。これは、データモデルが進化するたびに壊れる脆弱なインターフェースを作り出します。
私が現在の会社にVP of Platform Engineeringとして入社したとき、私たちのAPIは47のエンドポイントを持っており、これらは私たちのPostgreSQLスキーマと直接対応していました。1つの列名を変更するだけで、23の異なるクライアントアプリケーションでの更新を調整する必要がありました。技術的負債は、私たちの革新能力を圧迫していました。
代わりに、APIを独自のライフサイクル、バージョニング戦略、およびユーザーエクスペリエンスの考慮事項を持つ製品と考えてください。APIの消費者は、あなたのデータベースの正規化戦略や内部マイクロサービスアーキテクチャについては気にしません。彼らが気にしているのは、特定のタスクを効率的に達成することです。
たとえば、/users、/user_profiles、/user_preferences、および/user_settingsといった別々のエンドポイントを公開するのではなく、APIの消費者が実際に必要とするものを考えてみてください。ほとんどの場合、彼らは考え抜かれたリソースを返す、統合された/users/{id}エンドポイントを望んでいます。?fields=profile,preferencesのようなクエリパラメータを使用して、消費者が必要なものを正確にリクエストできるようにします。
私は、医療SaaS会社でこのアプローチを実装し、89のエンドポイントから34にAPIの表面積を削減しながら、実際に機能を増やしました。応答時間は43%減少しました。基本情報を組み立てるために複数のリクエストが必要となる冗長なやりとりを排除したからです。もっと重要なのは、私たちのAPIドキュメントが理解しやすくなり、開発者のオンボーディング時間が2週間から3日へと短縮されたことです。
鍵は、APIのドメインモデルを理解することです。これは、永続モデルとは大きく異なる場合があります。社内のフロントエンドチームや外部のパートナーと過ごす時間を大切にし、彼らのワークフローを理解してください。データベーステーブルではなく、彼らのメンタルモデルに基づいてリソースを設計します。
原則 2: HTTPステータスコードを適切に使用する(しかし、考えすぎない)
HTTPステータスコードはAPIとクライアントの最初のコミュニケーションの手段ですが、私はそれが誤用されたり完全に無視されたりしているのを常に見かけます。以前、すべての応答、特にエラーに対して200 OKを返し、実際のステータスがJSONフィールドに隠されているAPIを監査したことがあります。開発者は「常に成功している」と思っていましたが、実際にはすべてのHTTPクライアントライブラリのエラーハンドリングを破っていました。
すべての63のHTTPステータスコードを暗記する必要はありませんが、コアのものを正しく使用する必要があります。次は、12年間の運用経験に基づく私の実用的な分解です:
- 200 OK: コンテンツを返す成功したGET、PUT、またはPATCH
- 201 Created: リソースを作成する成功したPOST(Locationヘッダーを含める)
- 204 No Content: 何も返さない成功したDELETEまたは更新
- 400 Bad Request: クライアントが無効なデータを送信した(具体的な検証エラーを含める)
- 401 Unauthorized: 認証が必要または失敗
- 403 Forbidden: 認証されたが権限がない
- 404 Not Found: リソースが存在しない
- 409 Conflict: リクエストが現在の状態と矛盾する(重複作成、バージョン不一致)
- 422 Unprocessable Entity: 構文的には正しいが意味的には無効
- 429 Too Many Requests: レート制限を超えた(Retry-Afterヘッダーを含める)
- 500 Internal Server Error: あなたの側で何かが壊れた
- 503 Service Unavailable: 一時的な障害またはメンテナンス
401と403の区別に悩む多くの開発者がいます。401を「あなたが誰なのか分からない」と考え、403を「あなたが誰なのか分かっているが、それはできない」と考えてください。これは、クライアントに再認証が役立つかどうかを知らせるため重要です。
同様に、400と422の違いは微妙ですが役立ちます。400は形式が誤っているJSONや必須フィールドの欠落—基本的な解析に失敗するものを使用します。422は、アカウントに存在する以上の金額を送ろうとしたようなビジネスロジックの違反に使用します。この区別は、クライアントがエラーを適切に分類するのに役立ちます。
以前の会社では、適切なステータスコードの使用を実施し、APIエラーに関するサポートチケットが第一四半期に67%減少しました。開発者は、応答ボディを解析して成功や失敗を判断するのではなく、標準的なHTTPセマンティクスに依存できるようになりました。
原則 3: APIを初日からバージョン管理する(そして、正しく行う)
この教訓を苦い経験で学びました。2014年、私は「私たちは永遠に後方互換性を維持するだろう」と考えてバージョン管理なしでAPIを立ち上げました。6か月後、重要なビジネス要件をサポートするために破壊的な変更を加える必要がありました。私たちには、徐々に移行する方法がない1,200人のアクティブなAPI消費者がいました。その結果、強制的なアップグレードが行われ、私は...