webを支える技術メモ（第3部）

読書メモ
自分なりにまとめました。
プログラマとなり、半年？もうちょっと理解を深めたい

## HTTP
HTTPはweb上でやりとりするリソースの表現をクライアントとサーバーの間でやりとりするための[プロトコル](http://e-words.jp/w/%E3%83%97%E3%83%AD%E3%83%88%E3%82%B3%E3%83%AB.html)。クライアントはHTTPに従ってサーバーにリクエストを送り、レスポンスを得る。

### Basics

HTTPは、RESTの重要な特徴である、統一インターフェース、ステートレスサーバー、キャッシュなどを実現している、webの基盤となるTCP/IPをベースとしたプロトコル。

#### TCP/IPとは？
TCP(Transmission Control Protocol)とIP(Internet Protocol)はインターネット構成するネットワークプロトコル。

* 階層型プロトコル
> インターネットのネットワークプロトコルは階層型になっている
> 
> * ネットワークインターフェース層
>   - 階層の一番下。物理的なケーブルやネットワークアダプタに相当する 
>   
> * インターネット層
>   - ネットワークインターフェース層の上。ネットワークでデータを実際にやり取りする部分。TCP/IPでいう、IPがこの層に相当する。IPではデータを指定したIPアドレスを贈り先として、パケット単位でやり取りする。この際注意すべき点として、自分のネットワークインターフェースでデータを送り出すことだけを保証するということ。最終的な送り先までは保証しない。
>   
> * トランスポート層
>   - インターネット層の上。IPが保証しなかったデータの転送を保証するのがトランスポート層の役割。TCP/IPでいうTCPが相当する。TCPでは接続先の相手に対してコネクションをはる。このコネクションを使って、データの抜け漏れをチェックしている。
>   
> * アプリケーション層
>   - 最後にアプリケーション層。具体的なインターネットアプリケーション。例えば、メールやDNS、HTTPを実現する層。TCPでプログラムを作る際はソケットと呼ばれるライブラリを使うのが一般。ソケットはネットワークでのデータのやり取りを抽象化したAPI。接続、送信、受信、切断などの基本的な機能を備えている。とはいえ、ほとんどのプログラム言語はHTTPを実装したライブラリが標準で付いてため、そこまで意識する必要はない。しかし、サービスを開発する上で、パラメータなどが、プロトコルレベルでどのように動作するかを把握しておく必要がある。

#### リクエストとレスポンス
HTTPではクライアントが出したリクエストをサーバーで処理してレスポンスを返す。このようなプロトコルの事をリクエスト・レスポンス型のプロトコロル。

**クライアントで行われていること**
> * リクエストメッセージの構築
> * リクエストメッセージの送信
> * レスポンスが返るまで待機
> * レスポンスメッセージの受信
> * レスポンスメッセージの解析
> * クライアントの目的を達成するために必要な処理

**サーバーで行われること**
> * リクエストの待機
> * リクエストメッセージの受信
> * リクエストメッセージの解析
> * 適切なアプリケーションプログラムの処理の委譲
> * アプリケーションプログラムから結果を取得
> * レスポンスメッセージの構築
> * レスポンスメッセージの送信

#### HTTPメッセージ
クライアントがサーバにリクエストするときに送るリクエストメッセージと、クライアントがサーバからレスポンスを受け取る時に受けるレスポンスメッセージをまとめてHTTPメッセージと呼ぶ。

**リクエストメッセージの構成要素**

* リクエストライン：メソッド、リクエストURI、プロトコルバージョン
* ヘッダ：メッセージのメタデータ
* ボディ：本質的な情報。リソースを更新するリクエストを送る場合は、新しく作成するリソースの表現そのものが入る

**レスポンスメッセージの構成要素**

* ステータスライン：プロトコルバージョン、ステータスコード、テキストフレーズ
* ヘッダ：メッセージのメタデータ
* ボディ：本質的な情報

### HTTPメソッド
8つのメソッド

* GET：リソースの取得
* POST：子リソースの作成、リソースへのデータ追加、そのほかの処理
* PUT：リソースの更新、リソースの作成
* DELETE：リソースの削除
* HEAD：リソースのヘッダの取得
* OPTIONS：リソースがサポートしているメソッドの取得
* TRACE：自分宛にリクエストメッセージを返す試験
* ONNECT：プロキシ動作のトンネル接続への変更

#### HTTPメソッドとCRUD
HTTPのメソッドのうち、GET,POST,PUT,DELETEはこれら四つでCRUDEという性質をみたす、代表的なメソッド。CRUDEとは『Create』『Read』『Update』『Delete』というデータ操作の基本の処理のこと

#### POSTとPUTの使い分け
どちらのメソッドでもリソースを作成することが可能である。設計上の指針として次のような事実がある。
POSTでリソースを作成する場合は、リソースのURIを指定することができない。
PUTでリソースを作成する場合は、リソースのURIをクライアントで指定することができる。

#### べき等性と安全性

* べき等性
> ある操作を何回行っても必ず同じ結果が得られる

* 安全とは
>  操作対象のリソースの状態を変化させないこと

HTTPメソッドはその性質によって、以下のように分類することができる。

|メソッド    |      性質         |
|    :      |        :         |
|GET/HEAD   |べき等かつ安全       | 
|PUT/DELETE |べき等だが安全ではない|
|POST       |べき等でも安全でもない|


* GET,DELETE
> 同じリクエストを何度送信しても同じ結果が返ってくる。また、リソースの状態も変えることはない

* PUT,DELETE
> 同じリクエストを何度送信しても更新(PUT)された結果は同じになる。また、削除(DELETE)された結果も同じになる。しかし、リソースの中身を変えてしまっているので安全ではない。

* POST
> 同じリクエストを複数回送信すると、複数回データが更新されてしまうことがある(ショッピングサイトの二重注文など)。また、リソースの中身を変えてしまっているので安全でもない。

### ステータスコード
#### ステータスコードの分類と意味

レスポンスメッセージに含まれる。レスポンスメッセージの意味を伝える。

* 1xx
> 処理が継続していることを示す

* 2xx
> 成功

* 3xx
> 他のリソースへのリダイレクトを示す

* 4xx
> クライアントエラーを示す。原因はクライアントのリクエストにある

* 5xx
> サーバエラーを示す。原因はサーバ側にある

#### ステータスコードを意識して設計する
ステータスコードは大きく５つに分類でき、それぞれ意味がある。また、それらの分類を理解し、正しく扱うことが大切である。WebサービスやWebAPIでエラーが起きた時にどのステータスコードを返すかは、とても重要な設計の検討事項である。

### HTTPヘッダ
ヘッダは、メッセージのボディの対する付加的な情報、いわゆるメタデータを表現する。クライアントやサーバはヘッダを見てメッセージに対する挙動を決定する。
また、リソースへのアクセス権を設定認証方法や、通信回数と量を減らすキャッシュ、などを指定する\