REST APIの備忘録: GET/POSTリクエストの図解と基本

GET/POSTの違いや使い分けを図解してみました。自分でもよく忘れるので、シンプルに整理してみたつもり😅

GETとPOSTの違いが一目でわかる図解
他のメソッド(PUT/PATCH/DELETE)の使い方
API設計のポイント

必要な時に見返せるようにまとめてみたので、同じように「あれ？どっちだっけ？」となる方の参考になれば嬉しいです🙌 

## REST APIの基本

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2648069/3758fcc5-cec2-488a-8a0e-34a88953c7d7.png)

REST（Representational State Transfer）はWeb APIを設計する際のスタイルの一つ。

RESTの主な特徴（忘れないようにメモ）:
- リソース中心の考え方（ユーザー、記事など）
- HTTPメソッドを使ってリソース操作（GET, POST, PUT, DELETE）
- ステートレス（リクエストごとに独立している）

## HTTPメソッドの違い: 図で整理

私がよく混乱するのでイメージ図を作ってみました。

### 1. GET - データを取得するとき

```
ブラウザ/アプリ                               サーバー
    |                                         |
    |  ---> GET /api/users/123 ----------->  |
    |                                         |  ユーザー情報を検索
    |                                         |
    |  <--- {id:123, name:"山田太郎"} <----  |
    |                                         |
```

**GET の特徴**:
- URLにパラメータをつける（例: `/users?active=true`）
- データの読み取りだけ
- ブラウザで直接アクセス可能
- キャッシュされることがある

### 2. POST - 新しいデータを作るとき

```
ブラウザ/アプリ                               サーバー
    |                                         |
    |  ---> POST /api/users -------------->  |
    |       {name:"佐藤健", age:32}           |
    |                                         |  新しいユーザーを作成
    |                                         |
    |  <--- 201 Created  ------------------>  |
    |       {id:789, name:"佐藤健", age:32}   |
    |                                         |
```

**POST の特徴**:
- データはリクエストボディに入れる
- 新しいリソースを作成するときに使う
- 何度も同じリクエストを送ると複数のリソースができる
- URLには見えない（GETと違って）

## 自分がよく忘れるGETとPOSTの違い

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2648069/85a208ce-5302-4e16-ad7b-c98bb017c917.png)

| 特性 | GET | POST |
|------|-----|------|
| 何をするか | データを取得 | データを作成・送信 |
| データの送り方 | URLのクエリパラメータ | リクエストボディ |
| 見える？ | URLに見える（注意） | URLには見えない |
| ブックマーク | できる | できない |
| データ量 | 少ない（URL制限あり） | 多くても大丈夫 |
| 結果 | 何度実行しても同じ | 実行するたび変わる |

## 他のHTTPメソッド（使うときに見返す用）

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2648069/29245768-d5a7-448b-a78e-7d6b465136f7.png)

### PUT - データを更新（全部置き換え）

```
ブラウザ/アプリ                               サーバー
    |                                         |
    |  ---> PUT /api/users/789 ----------->  |
    |       {name:"佐藤健", age:33}           |
    |                                         |  ユーザー情報を更新
    |                                         |
    |  <--- 200 OK  ----------------------->  |
    |       {id:789, name:"佐藤健", age:33}   |
    |                                         |
```

### PATCH - データを部分更新

```
ブラウザ/アプリ                               サーバー
    |                                         |
    |  ---> PATCH /api/users/789 --------->  |
    |       {age:33}                          |
    |                                         |  age属性だけ更新
    |                                         |
    |  <--- 200 OK  ----------------------->  |
    |       {id:789, name:"佐藤健", age:33}   |
    |                                         |
```

### DELETE - データを削除

```
ブラウザ/アプリ                               サーバー
    |                                         |
    |  ---> DELETE /api/users/789 -------->  |
    |                                         |  ユーザーを削除
    |                                         |
    |  <--- 204 No Content  --------------->  |
    |                                         |
```

## リクエストとレスポンスの形（サンプル）

### リクエストの例

```
POST /api/articles HTTP/1.1
Host: api.example.com
Content-Type: application/json
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...

{
  "title": "REST APIメモ",
  "content": "忘れないようにメモしておく...",
  "tags": ["API", "REST", "備忘録"]
}
```

### レスポンスの例

```
HTTP/1.1 201 Created
Content-Type: application/json
Location: /api/articles/456

{
  "id": 456,
  "title": "REST APIメモ",
  "content": "忘れないようにメモしておく...",
  "tags": ["API", "REST", "備忘録"],
  "created_at": "2025-02-26T10:30:00Z"
}
```

## 覚えておきたいHTTPステータスコード

とりあえず最低限これだけは覚えておこう:

- **200** OK: うまくいった
- **201** Created: 新しく作成された
- **400** Bad Request: リクエストが間違ってる
- **401** Unauthorized: ログインしてね
- **403** Forbidden: 権限がない
- **404** Not Found: 見つからない
- **500** Internal Server Error: サーバーエラー

## APIを呼ぶコード例（自分用）

JavaScriptでAPIを呼び出す例（忘れがちなので）:

### GETでデータを取得

```javascript
// シンプルなfetch
fetch('https://api.example.com/api/users')
  .then(response => response.json())
  .then(data => console.log(data))
  .catch(error => console.error('Error:', error));

// async/await版
async function getUsers() {
  try {
    const response = await fetch('https://api.example.com/api/users');
    const data = await response.json();
    console.log(data);
  } catch (error) {
    console.error('Error:', error);
  }
}
```

### POSTで新しいデータを作成

```javascript
// 新規ユーザー作成
fetch('https://api.example.com/api/users', {
  method: 'POST',
  headers: {
    'Content-Type': 'application/json',
  },
  body: JSON.stringify({
    name: '田中次郎',
    email: 'tanaka@example.com',
    age: 30
  })
})
.then(response => response.json())
.then(data => console.log('Success:', data))
.catch(error => console.error('Error:', error));
```

## API設計時のメモ

自分がAPIを作るときに気をつけたいポイント:

- URIは名詞で（`/users`、`/articles`）
  - NG例: `/getUsers`、`/createArticle`
- アクションはHTTPメソッドで表現
  - GET /users（ユーザー一覧取得）
  - POST /users（ユーザー作成）
  - GET /users/123（特定ユーザー取得）
- レスポンスの形式は統一する

## まとめ

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2648069/b9fc6539-c584-4f20-92a2-05af4e53b0e0.png)

- **GET**: データを取る（読み取り専用）
- **POST**: 新しいデータを作る
- **PUT**: データを全部更新
- **PATCH**: データを一部更新
- **DELETE**: データを削除

APIを使うときは、まずどのHTTPメソッドを使うべきかを考える。
データの取得だけならGET、新しく作るならPOST、という感じ。

## マインドマップ
![マインドマップ (24).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2648069/4f271364-6e88-4a82-9036-4962ecd0facc.png)