Hypertext Transfer Protocol

歴史

イギリスの物理学者ティム・バーナーズ＝リーは1990年末、ロバート・カイリューと共に初のWebブラウザとWebサーバを作成した。ブラウザには通信をするためのプロトコルが必要だったので、二人はHTTPの最初期のバージョンを設計した。
以来インターネットの大部分をHTTP通信が占めるようになり、1998年にはインターネット上の通信の75%がHTTPによるものになった。
最初期のHTTP/0.9の仕様書は紙に印刷すれば1枚で済むような非常に簡素なドキュメントであったが、2度のバージョンアップを経たHTTP/1.1の仕様書は実に176ページ近くの分量に膨れあがった。

HTTP/0.9

1991年に最初にドキュメント化されたバージョン。メソッドは GET しかなかった。レスポンスは単純にドキュメントの内容を返してコネクションを切断するだけで、レスポンスコードの規定もない。下記は、HTTP/0.9 のリクエストの例。
GET /index.html

HTTP/1.1

1997年1月に RFC 2068 として初版が発表された。その後、2回改訂された。
名前ベースバーチャルホストをサポートした。インターネット人気に伴い多くの企業がWebサイトを持ち始めたが、当時はまだまだ企業が自前のWebサーバを運用するのは人員、効率の問題で難しく、ISPのサーバでホスティングをしていた。また、一社ごとに専用サーバを用意するほどのことでもないため、一台のサーバで複数のWebサイトを運用していた。
しかし、IPアドレスのみで相手を特定するHTTP/1.0はこれに対応できなかった。例えば、ある1台のサーバに foo.example.com と bar.example.com という二つの仮想Webサーバがあり、クライアントは http://foo.example.com/index.html にアクセスしたいとする。この場合はDNSサーバに foo.example.com のIPアドレスを問い合わせ、次にそのIPアドレスを使って該当サーバにアクセスし、GET index.html を要求することになる。しかし同じサーバ上にある bar.example.comもIPアドレスは同じであり、もし両方の仮想サーバに index.html というファイルが存在すれば、クライアントがどちらにアクセスしようとしているのか、判別できない。
対策としてはそれぞれにIPアドレスを付与する方法もあるが、IPv4の資源を無駄にすることになる。この問題を解決するため、Hostヘッダが追加された。
HTTP/1.1のリクエスト
GET /index.html HTTP/1.1Host: foo.example.com

HTTP/2

HTTP/2の目標はHTTP/1.1のトランザクション・セマンティクスとの完全な後方互換性を維持したまま非同期な接続の多重化、ヘッダ圧縮、リクエストとレスポンスのパイプライン化を実現することである。Googleによって立ち上げられ、GoogleのブラウザーであるChromeだけではなく、他にも、Opera、Firefox、Amazon Silk等が対応しているHTTP互換のプロトコルSPDYの人気が高まっていることに対応するために開発された。

HTTP/3

HTTP-over-QUIC（hq）としてIETFが開発していた新たな通信プロトコルが、HTTP/3へと改名される。
IETFが策定を進めているQUICはトランスポート層におけるプロトコルの名称であり、アプリケーション層プロトコルであるHTTP-over-QUICとの区別を明確にするため、このような名称変更に至った。
HTTP/2と比べ、多重化するストリームの取り扱いが下位層のQUICへ移行したこと、ヘッドオブラインブロッキングを回避するためのヘッダ圧縮の変更（HTTP/3用にQPACKが開発されている）などの差異がある。

通信の開始

他のプロトコル同様、クライアント側とサーバ側では役割が大きく異なる。HTTP通信を開始できるのはクライアント側のみである。
クライアント側がサーバにリクエストを送り、サーバがクライアントにレスポンスを返すのが最も典型的なHTTPのやりとりである。

接続

システム間でメッセージをやりとりするにはTCP接続を確立させる必要がある。
HTTP/0.9ではクライアントのリクエストごとにTCP接続を確立させる必要があったが、これは当時のWebサイトがシンプルなテキストベースであることが多かったためである。近年ではJavaScriptやアニメーション画像など、多数のオブジェクトが埋め込まれたWebサイトが一般的となってきており、これらのオブジェクトを取得するたびにTCP接続を確立するのはサーバやネットワークに大きな負担を強いるため、HTTP/1.1では持続的接続がサポートされることとなった。ただし、この機能が利用できるのはサーバ側がその要求を許可した場合のみである。

パイプライン

クライアントは前のリクエストに対するサーバの応答を待たずに別のリクエストを発行できる。

バーチャルホスト

上記参照

リダイレクト

別のURIに対して再度のメソッド実行を要求する機能である。301 Movedや303 See Otherなどのリダイレクトを指示するステータスコードとURIを受け取り、クライアントはこのURIに再度メソッドを実行する。

HTTPメッセージ

リクエストとレスポンスでやり取りされるデータは、HTTPメッセージと呼ばれる。
リクエストメッセージはリクエスト行・ヘッダーフィールド・ボディで構成され、レスポンスメッセージは、ステータス行・ヘッダーフィールド・ボディで構成される。ヘッダーフィールドとボディは空となる場合もある。
下にもっとも単純なクライアントとサーバ(www.google.co.jp:80)とのやり取りの例を挙げる。
クライアントのリクエスト:
GET / HTTP/1.0
この例では、リクエスト行のみで、ヘッダーフィールドとボディは空となっている。
リクエスト行はメソッド、URI、HTTPバージョンの3つの要素から構成され、それぞれスペースで区切られる。
メソッドはGET、URIは「/」、HTTPバージョンは1.0である。
GETはリソースを取得するためのメソッドであり、URIの「/」はルートリソースを対象にしたリクエストであることを示している。
サーバのレスポンス:
HTTP/1.0 200 OKCache-Control: privateContent-Type: text/htmlSet-Cookie: PREF=ID=72c1ca72230dea65:LD=ja:TM=1113132863:LM=1113132863:S=nNO7MIpW2o7Cqeu_; expires=Sun, 17-Jan-2038 19:14:07 GMT; path=/; domain=.google.co.jpServer: GWS/2.1Date: Sun, 10 Apr 2005 11:34:23 GMTConnection: Close<html><head><meta http-equiv="content-type" content="text/html; charset=Shift_JI S"><title>Google</title><style><!-- 
……以下省略 -->
先頭のステータス行はHTTPバージョン、ステータスコード、メッセージから構成される。
ステータスコードの「200」は処理の成功を表し、これを補足するメッセージが「OK」である。
2行目以降にヘッダフィールドが続く。
さらに空行を挟んで、レスポンスボディとなる。

HTTPヘッダフィールド

ヘッダの各要素は
フィールド名: 内容
のペアで構成される。
ブラウザの情報を表すUser-Agent、使用候補言語を表すAccept-Language、他ページへのリンクを辿った場合にそのリンク元ページのURLを表すRefererなどが代表的なフィールドである。
なお、リクエスト時のHostヘッダはHTTP/1.1では必須であるが、HTTP/1.0ではなくてもよい。
ただし、サーバがバーチャルホストを利用している場合は、Hostヘッダがないとリソース取得に失敗するので、たとえHTTP/1.0を使用していてもHostヘッダを付加しなければならない。

HTTPステータスコード

ステータスコードはサーバからのレスポンスで、リクエストの結果を通知する。3桁の数字から成り、おおまかな分類として、1xxは「情報」、2xxは「成功」、3xxは「リダイレクト」、4xxは「クライアントエラー」、5xxは「サーバエラー」を示す。

Basic認証

HTTP/1.1でBasic認証が定義されており最も単純なセキュリティ技術である。しかし仕様書を読むと定義を書いた著者自身が認証技術に疎いことがよくわかる。「基本認証を用いるくらいならなにも使わない方がまし」と主張する人もいる。通常サーバはステータスコード401で応答する。