API(Application Programming Interface)は、あるソフトウェアの機能を外部のプログラムから呼び出すための取り決めです。中でも HTTP でネットワーク越しに呼び出す Web API は、地図・決済・天気・生成AIなど、あらゆるサービス連携の土台になっています。本記事では、エンドポイントと HTTP メソッド、リクエスト/レスポンスの中身、REST の考え方、認証・認可、そして CORS やレート制限といった実際のつまずきまでを整理します。
1. API とは — 「使い方の取り決め」
API は、機能を提供する側が「この形式で呼べば、この形式で返します」と約束した窓口の仕様です。レストランのメニューに例えられます。客(呼び出す側)は厨房の作り方を知らなくても、メニューに書かれた名前で注文すれば料理が出てきます。内部の実装を知らなくても使えるという点が API の本質です。
- API:広い意味の言葉。OS のシステムコールも、ライブラリの関数も API です。
- Web API:そのうち HTTP を使ってネットワーク越しに呼ぶもの。今日「API を叩く」と言えばほぼこれを指します。
- 提供側は内部実装を自由に作り替えられます。約束(インターフェース)さえ変わらなければ、呼び出す側は影響を受けません。
この「約束」を守ることが提供側の責任であり、だからこそ API にはバージョン(/v1/ など)が付きます。約束を壊す変更(破壊的変更)をするときは、新しいバージョンとして分けるのが定石です。
2. エンドポイントと HTTP メソッド
Web API の呼び出し先 URL をエンドポイントと呼びます。エンドポイントは「どのリソース(対象)か」を表し、HTTP メソッドが「そのリソースに何をするか」を表します。
例:https://api.example.com/v1/users/42 は「ID が 42 のユーザー」というリソースを指します。
| メソッド | 意味 | 性質 |
|---|---|---|
| GET | 取得する(GET /v1/users/42) | 安全(サーバの状態を変えない)・べき等 |
| POST | 新規作成する(POST /v1/users) | べき等でない(2回送れば2件できうる) |
| PUT | 丸ごと置き換える(PUT /v1/users/42) | べき等(何回送っても結果は同じ) |
| PATCH | 一部だけ更新する | 実装によりべき等とは限らない |
| DELETE | 削除する(DELETE /v1/users/42) | べき等(すでに無ければ変化なし) |
べき等(idempotent)とは「同じリクエストを何度送っても、結果の状態が変わらない」性質のことです。通信エラー時に安全に再送できるかを左右するため、実務では重要な区別になります。POST はべき等でないため、決済のような処理では冪等キー(Idempotency-Key ヘッダ等)を付けて二重実行を防ぐ設計がよく使われます。
取得条件はクエリ文字列で渡します。例:GET /v1/users?role=admin&limit=20。値に日本語や記号を含む場合はURLエンコードが必要です。
3. リクエストとレスポンスの中身
HTTP のやり取りは、ヘッダ(メタ情報)とボディ(データ本体)に分かれます。Web API ではボディに JSON を使うのが一般的です。
POST /v1/users HTTP/1.1
Host: api.example.com
Content-Type: application/json
Authorization: Bearer eyJhbGciOi...
Accept: application/json
{"name": "田中太郎", "role": "admin"}
これに対する応答は、ステータスコードとヘッダ、そして JSON のボディで返ります。
HTTP/1.1 201 Created
Content-Type: application/json
{"id": 42, "name": "田中太郎", "role": "admin"}
ステータスコードは「どうなったか」を 3 桁で表す、API 読解の要です。
| コード | 意味 | 典型的な場面 |
|---|---|---|
| 200 OK | 成功 | GET でデータが返った |
| 201 Created | 作成成功 | POST でリソースを作った |
| 204 No Content | 成功・本文なし | DELETE が完了した |
| 400 Bad Request | リクエストが不正 | 必須項目が無い・JSON が壊れている |
| 401 Unauthorized | 認証されていない | トークンが無い・期限切れ |
| 403 Forbidden | 権限が無い | 認証済みだが操作を許されていない |
| 404 Not Found | 対象が無い | 存在しない ID を指定した |
| 429 Too Many Requests | 呼びすぎ | レート制限に達した |
| 500 Internal Server Error | サーバ側の障害 | API 提供側の不具合 |
4. REST の考え方 — リソース指向とステートレス
REST(Representational State Transfer)は、Roy Fielding が 2000 年の博士論文で示したアーキテクチャスタイルです。プロトコルでも規格でもなく「Web らしく作るための原則」であり、その原則に沿った API を RESTful な API と呼びます。
- リソース指向:URL は名詞(対象)にし、動作は HTTP メソッドで表します。
/v1/users/42にDELETEであって、/v1/deleteUser?id=42ではありません。 - ステートレス:サーバはリクエスト間の文脈を保持しません。1 回のリクエストに必要な情報(認証トークンなど)を毎回すべて含めるため、サーバを増やして負荷分散しやすくなります。
- 統一インターフェース:同じ規則(メソッド・ステータスコード・表現形式)を使い回すので、新しい API でも読み方を推測できます。
- キャッシュ可能:GET は安全なので、HTTP のキャッシュ機構をそのまま活かせます。
REST の利点は、HTTP の既存の仕組み(メソッド・ステータスコード・キャッシュ)をそのまま使えることです。学習コストが低く、ツールやプロキシ、CDN との相性も良いため、Web API の事実上の標準になっています。
5. 認証と認可 — APIキー・Bearerトークン・OAuth
公開データ以外の API では、「誰として呼んでいるか」を示す必要があります。認証(誰か)と認可(何をしてよいか)は別の概念です。
- API キー:発行された文字列をヘッダに載せます。単純ですが、キー=そのまま権限なので秘匿が命です。
- Bearer トークン:
Authorization: Bearer <token>の形式(RFC 6750)。「この券を持つ者(bearer)を通す」という意味で、中身に JWT を使うことが多いです。有効期限があるのが利点です。 - OAuth 2.0:ユーザーのパスワードを渡さずに、第三者アプリへ限定的な権限を委譲するための認可フレームワーク(RFC 6749)。「Googleでログイン」の裏側で使われます。
6. つまずきやすい点 — CORS・レート制限・エラー処理
API を実際に呼び始めると、ほぼ必ず出会う 3 つの壁があります。
CORS(クロスオリジン制約)
ブラウザは、あるサイトの JavaScript が別オリジン(ドメイン・スキーム・ポートの組)の API を無制限に読むことを既定で禁じています。許可するには、API 側が Access-Control-Allow-Origin ヘッダを返す必要があります。ここで重要なのは、CORS はブラウザが課す制約であって、サーバ同士の通信や curl には関係しないという点です。「curl では動くのにブラウザだと失敗する」なら、まず CORS を疑います。
レート制限
多くの API は「1 分あたり N 回まで」といった上限を設け、超えると 429 Too Many Requests を返します。Retry-After ヘッダや残回数ヘッダが返ることが多いので、それに従って待ちます。再試行は指数バックオフ(1秒、2秒、4秒…と間隔を空ける)にし、闇雲な即時リトライは避けます。
エラー処理とタイムアウト
ネットワーク越しの呼び出しは失敗するのが普通です。ステータスコードを必ず確認し(fetch は 404 や 500 でも例外を投げません)、タイムアウトを設定し、再試行してよいのはべき等な操作だけ、と決めておきます。
const res = await fetch('https://api.example.com/v1/users/42', {
headers: { 'Authorization': 'Bearer ' + token, 'Accept': 'application/json' }
});
if (!res.ok) throw new Error('API error: ' + res.status);
const user = await res.json();
7. REST 以外の選択肢 — GraphQL・gRPC・WebSocket
REST が万能というわけではありません。用途に応じて他の方式も使われます。
| 方式 | 特徴 | 向いている場面 |
|---|---|---|
| REST | URL=リソース、HTTPメソッドで操作。JSON が主流 | 汎用のWeb API。キャッシュを活かしたい |
| GraphQL | クライアントが必要なフィールドを指定して取得 | 画面ごとに必要データが大きく異なる場合 |
| gRPC | スキーマ定義から生成、バイナリで高速 | マイクロサービス間の内部通信 |
| WebSocket | 接続を維持し双方向にやり取り | チャット・通知など、サーバから押し出したい場合 |
迷ったら REST から始めるのが定石です。学習コストが低く、ツールが揃っており、必要になったときに他方式へ移行・併用できます。GraphQL は「1画面のために何度も API を呼ぶ(アンダーフェッチ)/使わないフィールドまで返る(オーバーフェッチ)」が痛みとして現れてから検討すれば十分です。
Free Tool JSON Formatter で API レスポンスを読む 1行にまとまった API のレスポンスを、ブラウザ内で整形して構造を確認できます。文法エラーの位置も分かります。よくある質問(FAQ)
API と Web API の違いは何ですか?
API はソフトウェアの機能を外部から呼び出すための取り決め全般を指す言葉で、OS のシステムコールやライブラリの関数も API です。そのうち HTTP を使ってネットワーク越しに呼び出すものを特に Web API と呼びます。今日「API を叩く」と言うときは、多くの場合 JSON をやり取りする Web API を指しています。
REST と GraphQL はどちらを使うべきですか?
用途によります。リソースの取得・作成・更新・削除が中心で、HTTP のキャッシュやステータスコードをそのまま活かしたいなら REST が扱いやすい選択肢です。画面ごとに必要なフィールドが大きく異なり、複数リソースをまとめて取得したい(オーバーフェッチ・アンダーフェッチを避けたい)場合は GraphQL が向きます。まず REST で始め、必要が生じたときに検討するのが現実的です。
API キーをフロントエンドの JavaScript に書いても大丈夫ですか?
秘密の API キーをブラウザ側のコードに書いてはいけません。JavaScript のソースも通信内容も利用者から見えるため、キーはそのまま漏えいします。秘密キーが必要な呼び出しは自社のサーバ側で行い、ブラウザからは自社サーバの API を呼ぶ構成にします。どうしてもブラウザから直接呼ぶ場合は、公開前提の(権限を絞った)キーを使い、リファラ制限やドメイン制限、レート制限を併用します。