HTTP圧縮とはHTTP通信を自動的に圧縮する(WebサーバがHTTP通信を圧縮し、ブラウザでその圧縮を解く)ことです。
メリット
通信量を減らし全体的なスループットをあげることができます。モバイルのような帯域の限られている環境では特に有効です。
デメリット
圧縮および伸張にCPUパワーを必要とします。
- サーバ:HTTP圧縮を有効にすると配信能力が低下します。
- クライアント:スマートフォンの普及とともにCPU負荷および消費電力の増加は大きな問題ではなくなっています
プロトコル
- クライアント(ブラウザ)リクエスト
- 以下のようにAccept-Encodingを付けてGETリクエストを送信します。
- GET /test.html HTTP/1.1
Host: example.com
Accept-Encoding: gzip, deflate
- GET /test.html HTTP/1.1
- 以下のようにAccept-Encodingを付けてGETリクエストを送信します。
- サーバレスポンス
- 以下のようにContent-Encodingが付けられたレスポンスが返され、httpペイロードは指定された方法で圧縮されます。
- HTTP/1.1 200 OK
Date: mon, 23 Mar 2016 22:38:34 GMT
Server: Apache/1.3.3.7 (Unix) (Red-Hat/Linux)
Last-Modified: Wed, 08 Jan 2003 23:11:55 GMT
Accept-Ranges: bytes
Content-Length: 438
Connection: close
Content-Type: text/html; charset=UTF-8
Content-Encoding: gzip
gzip圧縮されたペイロード
- HTTP/1.1 200 OK
- 以下のようにContent-Encodingが付けられたレスポンスが返され、httpペイロードは指定された方法で圧縮されます。
圧縮方式
Accept-encoding、Content-encodingで指定できる圧縮方法には以下のようなものがあります(抜粋です)。
- 標準
- identity
- 変換していないことの明記
- deflate
- アルゴリズム:LZ77、ハフマン符号
- フォーマット:zlib
- gzip
- アルゴリズム:LZ77、ハフマン符号
- フォーマット:Gnu zip
- identity
- 非標準
- bzip2
- 特徴:deflateやgzipよりも圧縮率が高い
- アルゴリズム:Burrows-Wheeler transform (BWT) aka ブロックソート
- フォーマット:bzip2
- brotli
- 特徴:Googleが開発した最新(2015年発表)アルゴリズムを使用、HTTPSのみをサポート(HTTPSを推進するというポリティカルな理由)
- アルゴリズム:LZ77、ハフマン符号、2nd order context modeling
- フォーマット:brotli
- bzip2
Web(オリジン)サーバにおけるサポート
- apache
- mod_deflateによりサポートされます
- 圧縮はリクエスト毎に行われます
- mod_deflateによりサポートされます
- nginx
- gzip onの設定により有効化されます
Cacheサーバ(CDN)におけるサポート
Cacheサーバ(CDN)は、以下の2種類のモードでHTTP圧縮をサポートします
オリジン依存モード
これは、RFCに規定されたWeb Cacheの基本動作で、多くのCDNがサポートしている可能性があります。
基本的な動作として、Cacheサーバは圧縮を行わず、複数のコンテンツ(たとえば、非圧縮html、gzip圧縮html、deflate圧縮html)を保持します。そして以下のようなフローで保存したコンテンツをクライアントに送信します:
- オリジンサーバが送信した圧縮済みHTTPペイロードをそのまま保存する
- Encoding別にキャッシュを生成する
- クライアントからの要求(Accept-Encoding)にあわせたキャッシュをクライアントに送信する
このEncodingに合わせたキャッシュオブジェクトの識別は、次のようにVaryヘッダ(RFCで規定されたCache動作指定)をオリジンサーバが付与することで実現できます。また、apacheのmod_deflateは自動的にVaryを付与します:
- HTTP/1.1 200 OK
Date: mon, 23 Mar 2016 22:38:34 GMT
Server: Apache/1.3.3.7 (Unix) (Red-Hat/Linux)
Last-Modified: Wed, 08 Jan 2003 23:11:55 GMT
Accept-Ranges: bytes
Content-Length: 438
Connection: close
Content-Type: text/html; charset=UTF-8
Content-Encoding: gzip
Vary: Accept-Encoding
注意点
Cacheサーバは(Content-Encoding別にオブジェクトをキャッシュしているのではなく)、Accpet-Encoding別にオブジェクトをキャッシュしています。つまり、クライアントが”Accept-Encoding: gzip, deflate”を送信したときにサーバが返したencodingのオブジェクトがキャッシュされ、それ以降の”Accept-Encoding: gzip, deflate”に対して使用されます。そして、”Accept-Encoding: gzip”のように単独でencodingが指定されたリクエストに対しては、別のオブジェクトが生成されます。
CDNでは、無条件にVary動作を許すとひとつのURLに対して複数のオブジェクト(数十程度:Accept-Encodingの組み合わせ分)が生成される可能性があるため、何らかの制限をかけている場合があります。たとえば、「gzip(もっとも多くの場合に使用されてている)のみを許し、それ以外は無視する」というような制限がかかっている場合があります。
Cache上圧縮モード
オリジンサーバでは圧縮を行わずCacheサーバで圧縮を行います。この機能は各CDNに依存した実装になります。