http/2の現状とこれから
TRANSCRIPT
自己紹介
• 名前:大津繁樹
• 所属:株式会社インターネットイニシアティブ(IIJ) アプリケーション開発部
• Twitter: @jovi0608
• ブログ:ぼちぼち日記 http://d.hatena.ne.jp/jovi0608/
• GitHub: https://github.com/shigeki/
• 新技術の検証・評価を行ってます。 (Node.js, io.js,SPDY, HTTP/2,HTML5)
• iij-http2の開発を通じてIETFのHTTP/2標準化作業に参画中
HTTP/2 はRFC化目前です
• HTTP/2• IESGレビュー終了。コメントを受けてドラフトを改訂。その後承認見込
• HPACK• IESG承認済(1/23)
発行プロセスが順調なら桜が咲く前にはRFC化かも
Ethernet
IP(v4/v6)
TCP
TLS
HTTP/2Frame Layer
HTTP/1.1Semantics
内容
•これまで• HTTP/1.1の問題点のおさらい (+デモ)
•現状 (SPDY, HTTP/2)• SPDY, HTTP/2の対応状況
• HTTP/2の最終仕様の概要 (いくつかピックアップ)
•これから• HTTP/2の拡張→ HTTP/3の展望
• HTTP/2の応用:WebPush + Push API (Service Worker+ Server Push)
• 新プロトコル: QUIC (+デモ)
HTTPプロトコルの年表
1990 1995 2000 2005 2010 2015Webの始まり
HTTP/0.9 HTTP/1.0RFC1945
HTTP/1.1RFC2068
HTTP/1.1RFC2616
HTTP/1.1RFC7230-5
HTTP/2
SPDY/2
SPDY/3
SPDY/3.1
httpbis WG
暗黒の時代
HTTP-NG中止
HTTP/2の全二重多重化通信
クライアント サーバ
1つのTCP接続
ストリーム(id:1)
フレーム
フレーム
ストリーム(id:3)
フレーム
フレーム
ストリーム(id:5)
フレーム
フレーム
HTTPリクエストレスポンス
HTTPリクエストレスポンス
HTTPリクエストレスポンス
仮想的なストリームチャンネルを生成して多重化を実現
後でデモします。
HTTP/1.1は非効率なプロトコル
0
10
20
30
40
50
60
10 15 20 25 30 35 40 45
輻輳ウィンドウサイズ
(mss
)
時間(sec)
HTTP/1.1+SSLの輻輳ウィンドウサイズの変遷
SSL1
SSL2
SSL3
SSL4
SSL5
SSL6
6本のTCPがバラバラに輻輳制御。帯域を有効に使いきれてない
HTTP/2(SPDY)は効率的なプロトコル
0
10
20
30
40
50
60
60 65 70 75 80 85 90 95
輻輳ウィンドウサイズ
(mss
)
時間(sec)
SPDY利用時の輻輳ウィンドウサイズの変遷
SPDY
1本のTCPで最高速まで利用。帯域を最大限に効率的に使っている。
3. HTTP/1.1は処理が煩雑なテキストプロトコル
HTTP/1.1 200 OKContent-Type: image/jpegTransfer-Encoding: chunkedTrailer: Foo
123{binary data}0Foo: bar
Status-Lineは一行目 空白は1つ
ヘッダ名は大文字・小文字区別せず
ヘッダ領域の区切りはCRLF一つ
:の後に空白を許可
CRLFで改行、複数行対応は廃止
レスポンスデータがchunkedであり、サイズはまだ不定
一番最後にFooヘッダが付与されることを宣言
続くデータが123バイトであることを宣言
データ終了の合図
Trailヘッダ
chunk終了合図のCRLF
HTTP/2はきっちりしたバイナリープロトコル
00 00 00 01
01 04
00 00 1a
88 5c 82 08
・・・・・・
73 ff
00 00 00 01
00 00
00 00 7b
{binary data}
:status = 200content-length = 123content-type = image/jpegtrailer = Foo
HEADERS
DATA
フレーム長:28バイト
フレーム長:123バイト
フレームタイプ:HEADERS, END_HEADERSフラグ
ストリームID: 1
ストリームID: 1
フレームタイプ:DATA, フラグなし
(* 記載スペースの都合上Trailer HEADERSは省いています)
データの位置・サイズ・型
が明確
デモ:HTTP/2(SPDY)は、本当にHTTP Head of Line Blockingを回避できているのか?
クライアント
画像サーバA
画像サーバB
ReverseProxy
HTTP/2多重化通信
レスポンスが速い
レスポンスが遅い
HTTP/2の対応状況
• Firefox35: デフォルト有効(h2-14)
• Chrome41: デフォルト有効(h2-14)
• IE on Windows10 Technical Preview: h2-14
• Google: h2-14,h2-15
• Twitter: h2-15
(注: h2-15とh2-14は技術的に同じ仕様です)
HTTP/2の最終仕様概要•前回のHTML5 Conference でも話をしましたので、
http://www.slideshare.net/shigeki_ohtsu/html5-conf2013-http2iijohtsu
更新された中でいくつかトピックスを紹介します。
HTTP/2プライオリティ
クライアント ReverseProxy
コンテンツ
HTML
画像
CSS, jS
HTML
CSS JS
画像1 画像2 画像3 画像4
依存性と重みを指定
weight:16 weight:16
プライオリティのユースケース
• ファイルタイプ(HTML/CSS/JS/画像)に応じた返答順序の指定
• タブ切り替えによる重みの上げ下げ• 分割されたビデオデータなど順番が明示的に決められている場合
Firefox38のプライオリティ依存機能(h2-16)Stream:0x0
Stream:0x3Leader
Stream:0x5Unblocked
Stream:0x7Background
weight:201 weight:1weight:101
Stream:0xbFollower
Stream:0x9Speculative
weight:1weight:1
css,jsファイル
html,images等その他
XHR非同期js
明示的なバックグラウンドリクエスト
beacon等大きなバックグラウンドリクエスト
idleストリーム
HTTP/1.1セマンティクスと非互換なところ
•ホップ-バイ-ホップヘッダの利用禁止• ホップ-バイ-ホップ間の通信制御はHTTP/2フレームの役割であるため、
HTTPヘッダによる制御を禁止。
• Connection, Transfer-Encoding, TE, Upgrade, Keep-Alive, Proxy-Connectionヘッダは利用禁止。
• TE: trailers だけ例外
• Status Code: 101 (Switching Protocols) も禁止
クライアント プロキシ プロキシ プロキシ サーバ
hophop hop
End-To-Endヘッダだけ許可
TLS利用条件の厳格化• HTTP/2は、仕様上平文での接続(http://)も規定されており、TLS利用は必須ではなくなりました。
•ただしChromeやFirefoxではTLS利用したHTTP/2のみサポート。MSがHTTP/2の平文通信に賛同しているが、IEでの実装はまだ。
• HTTP/2の利用は実質的にTLSを用いたものが中心になる見込み。
•現行のTLS1.2でもまだセキュリティ的に十分でないのでTLS利用条件を厳格化して対応• renegotiation, compressionの禁止
• SNI利用の必須
• PFS(Perfect Forward Secrecy), AEAD利用の必須(RC4,CBCモード利用禁止)
•検討中のTLS1.3の仕様を先取りしたもの
HTTP/2の拡張→HTTP/3の展望
1. ALT-SVCフレーム• 負荷分散やメンテなどのサーバ切り替え、プロトコルの切り替え
2. WebSocket over HTTP/2• HTTP/2仕様を拡張してWebSocket多重化を実現
3. 明示的プロキシ機能• Chrome for Android の DATA Compression機能の仕組みを標準化へ
• プロキシとの間をHTTP/2で接続。平文http:// のコンテンツキャッシュ
4. 日和見暗号(opportunistic encryption)• http:// の通信でサーバ認証せずに暗号化を行う。
HTTP/2の応用WebPushいろんな場面でプッシュ通知は必要
1. ブラウザ上でアプリが動作している時• チャット等の通常のアプリ通知
2. ブラウザは立ち上げているがアプリは動作していない時• SNSのメッセージやweb feedを受ける
3. ブラウザも立ち上げていない時• WebRTCによる入電でウェブアプリを立ち上げる
4. 1つのブラウザでアプリを複数インスタンス立ち上げている。又は、異なるブラウザで同一のアプリを動作させている。• そのうちの1つにだけプッシュ通知したい。• 全部にプッシュ通知をブロードキャストしたい。• 複数アカウントでメール利用など。
HTTP/2の応用 Service Worker+ Server Push
プッシュサーバ
アプリケーションサーバ
Webアプリの通信HTTPS必須
5. Service Worker上でPushイベントが発生。
ArrayBuffer, blob, json, textの形式でプッシュデータを取り出せる。
2. HTTP PUTのリクエストボディにプッシュメッセージを付けて送信
4. HTTP/2サーバプッシュを利用してクライアントに通知
3. 複数アプリのプッシュ通知をチャネルで区別し、一つの接続上で送信
1. クライアントからプッシュサーバ名と登録IDを通知
ServiceWorker
ウェブアプリ
ブラウザ
Push API
クライアント
Service Workerからこう見える// 登録されたService Workerのコード
this.onpush = function(event) {
console.log(event.data);
// event.dataは、ArrayBuffer, blob, json, text形式
// ここでIndexedDBにdataを書き込んだり、
//開いているウィンドウにdataを送ったり、
// Notificationを表示したりなどができる。
}
Web Pushは、複数のブラウザ、複数のアプリインスタンス、アプリの起動・停止中等様々な場面でもプッシュ通知が行える
新プロトコル: QUIC(Quic UDP Internet Connections)
IP(IPv4/IPv6)
UDPTCP
TLSQUIC
SPDY
HTTP
暗号化・認証
セッション確立、フロー制御エラー補正, 輻輳制御
• Googleが独自に開発しているプロトコル
• UDP上でTCP+TLS相当+αの機能を実装• 最短0-RTTで再接続、暗号通信を必須化• TCPと同様の輻輳制御で帯域の公平化• 独自の誤り訂正と再送機能でパケットロスによるTCPのHead of Line Blockingを回避
• Googleの全サービスで運用中、Chromeのフィールドテスト中(*)• Stable版: 0.2%(Desktop), 2%(Android)• Beta版: 25%(Desktop), 50%(Android)
• 知らない間に使っているかも?
• 今年にライブラリ化を予定
(* 割合は2014/08時点のGoogleの公表値)