HTTP/3入門

第5章HTTP/3の拡張と応用 ~ 機能を追加し、より効率的に、より便利に

本章では、HTTP/3に機能の追加や変更を行う拡張についてと、HTTP/3を利用した応用プロトコルについて解説します。

HTTP/3の拡張 ─⁠─ 機能の追加や変更を行う

HTTP/3は拡張性を有しており、拡張仕様として機能の追加や既存の動作の変更を行えます。本節では、拡張とはどういったものなのかと、拡張事例を説明します。

ただし、HTTP/3自体の標準化が終わっていないため、HTTP/3の拡張事例はまだ目立ったものがありません。そのため事例としてはHTTP/2とQUICの拡張を紹介します。HTTP/2やQUICも、HTTP/3と同様に拡張性を有しています。

拡張可能な箇所

HTTP/3では、次の項目が拡張可能です。

  • フレームタイプ
  • SETTINGSパラメータ
  • エラーコード
  • 単方向ストリームタイプ

これによりたとえば、新しいフレームのタイプを定義できます。新しいフレームを定義するにあたっては、パラメータを交換するためにSETTINGSパラメータを新しく定義したり、エラーハンドリングのためにエラーコードを新しく定義したりするのが一般的です。同様に、新しい単方向ストリームのタイプも定義できます。

まったくの架空ですが、新しいフレームのタイプとしては、次のようなものが考えられます。

COPRESSED_DATAフレーム
コンテンツをプロトコルの機能として圧縮して送信する
DOMAINフレーム
今後必要となるであろうドメイン情報を通知する

拡張に対応しているかどうかの確認

拡張を使うにあたっては、相手が対応しているかどうかを確認する必要があります。どのように確認するかは拡張仕様ごとに定義しますが、ここでは一般的な戦略を紹介します。

HTTP/3の仕様上、実装は未知のフレームタイプやSETTINGSパラメータは無視するよう規定されています。無視されてもよいデータを送る場合、エンドポイントは新しく定義したフレームを確認せずにいきなり送信できます。先に挙げたDOMAINフレームは、処理できれば有用かもしれませんが、無視されても動作上は問題ないので、いきなり送信できます。

一方で、先に挙げたCOPRESSED_DATAフレームは、無視されるとHTTPメッセージが送れず困ってしまいます。このような場合は、新しく定義したSETTINGSパラメータでクライアントとサーバがお互いにこの拡張に対応していることを確認し合い、合意を得たうえで拡張を使用する必要があります。

識別子の登録

プロトコルで定義されるタイプ値やIDといった識別子の値は、国際的非営利組織のIANAInternet Assigned Numbers Authorityが一元管理しています。HTTP/3においても、拡張可能な箇所に新しいものを定義する場合はIANAに登録します。たとえば、新しく定義したフレームのタイプ値として0x99を割り当てたとします。このとき、ほかの拡張仕様とその番号が重複すると、プロトコルは正しく動作できません。そのため、IANAに登録する必要があります。一般的には、標準化される中で番号が登録されます。

登録されている値は、IANAのページより、HTTP/3HTTP/2QUICをそれぞれ確認できます。

HTTP/2の拡張

本項では、HTTP/2の拡張を紹介します。

ALTSVCフレーム ─⁠─ 提供できるサービスの通知

第3章でRFC 7838のHTTP Alternate Servicesを紹介しました。この仕様は、サービスの別の提供方法をクライアントに通知するしくみです。第3章では、HTTP/1.1やHTTP/2の通信時にHTTP/3もサポートしていることをクライアントに通知しました。

この仕様では、第3章のようにHTTP/1.1もしくはHTTP/2においてAlt-Svcヘッダで通知することもできますが、HTTP/2ではALTSVCフレームを使うこともできます。両方とも伝えられる情報は同じですが、ATLSVCフレームはレスポンスを送信するとき以外でも送れます。

ALTSVCフレームは、次の2つをクライアントに通知します。

  • オリジン(httpsといったURLのスキーム、ドメイン名、ポート番号)
  • そのオリジンを提供できる代替エンドポイントおよび代替プロトコル

この拡張はいきなり送信され、クライアントが対応していなかった場合は無視されます。

ORIGINフレーム ─⁠─ 提供できるオリジンの通知

HTTP/2は、名前解決したサーバのIPアドレスが同一かつ、TLSハンドシェイク時のサーバ証明書がカバーするドメイン名であれば、複数のドメイン名に対するリクエストを1つのTCPコネクションでまかなうことができます。証明書にはたとえば、ワイルドカード証明書を使うことが考えられます。たとえば、a.example.comb.example.comへのリクエストがこの条件を満たせば、クライアントはTCPコネクションを再利用します。

ただし、TLSのハンドシェイク中、クライアントが送信した接続先ドメイン名を示すSNIServer Name Indicationを用いて、サーバもしくはプロキシで何らかの処理を行う場合などは、TCPコネクションを再利用できないことがあります。

そこで、RFC 8336のThe ORIGIN HTTP/2 Frameでは、サーバが提供できるオリジンのリストをクライアントに通知可能にします。これにより、クライアントがTCPコネクションを再利用できるかを判断できます。

この拡張もいきなり送信され、クライアントが対応していなかった場合は無視されます。

WebSockets with HTTP/2 ─⁠─ 双方向通信

HTTPでは、リクエストから開始されレスポンスが返されます。Webの利用が広がる中で、たとえばゲームといったデータを双方向に頻繁にやりとりするような用途にHTTPは向いていませんでした。そのようなユースケースをカバーするために、HTTPを使ってクライアントとサーバ間でTCPコネクションを確立したのち、そのTCPコネクション上で任意のタイミングでどちらからでもメッセージを送信可能にするWebSocketという技術が登場しました。

WebSocketをHTTP/2上でも行えるようにした拡張が、RFC 8441のBootstrapping WebSockets with HTTP/2です。HTTP/2では1つのTCPコネクション上に複数のストリームを持つので、そのうちの1つをWebSocket用通信に切り替える方法を定義しています。

この拡張は、クライアントとサーバがお互いに対応していることを確認し合い、合意を得たうえで使用します。そのために、SETTINGS_ENABLE_CONNECT_PROTOCOLパラメータを送り合います。

合意が得られたら、クライアントからHTTPのCONNECTメソッドのリクエストを、擬似ヘッダの:protocolとともに送信し、WebSocket通信を開始します。HTTP/2ですので、リクエストはフレームで送信されます。

WebSocketsを開始するリクエスト
:method = CONNECT
:protocol = websocket
:scheme = https
:path = /chat
:authority = server.example.com
sec-websocket-protocol = chat, superchat
sec-websocket-extensions = permessage-deflate
sec-websocket-version = 13
origin = http://www.example.com

HTTPのCONNECTメソッドについて補足すると、このメソッドは、通信の中継を行うプロキシサーバに接続し、最終的な通信相手であるサーバに対して通信データをトンネリングするために使用します。HTTP/1.1ではTCPコネクションの全データをトンネリングしますが、HTTP/2とHTTP/3ではCONNECTメソッドのリクエストを送ったストリームのデータのみがトンネリングされます。拡張仕様では、プロキシサーバ以外の通信にも使用されます。

上記で登場しているWebSocket関連のヘッダ群は、WebSocketの仕様で定義されています。

QUICの拡張

本項では、QUICの拡張を紹介します。

DATAGRAMフレーム ─⁠─ アプリケーションデータの柔軟な送信

QUIC上で送受信されるアプリケーションデータは、パケットロスが起こっても再送されます。仕様上、再送されないアプリケーションデータはありません。また、パケットの順番が入れ替わったとしても、同一QUICストリーム上のアプリケーションデータは送信された順に並びなおされて処理されます。

しかし、実際のユースケースとしては、リアルタイムの動画配信など、遅れたデータは不要な場合があります。そのようなユースケースをカバーするために、An Unreliable Datagram Extension to QUICという拡張仕様が定義されました。この仕様で定義されているDATAGRAMフレームは、QUICの拡張フレームです。

補足情報

DATAGRAMフレームの仕様は、2022年3月にRFCとして出版されました。仕様の内容については、誌面での説明から変更はありません。

RFCは次のリンクから参照できます。

この拡張も、クライアントとサーバがお互いに対応していることを確認し合い、合意を得たうえで使用します。そのために、QUICコネクションの確立時にトランスポートパラメータとしてmax_datagram_frame_sizeを送り合います。

DATAGRAMフレームは、データのみを運ぶ単純なフレームです。このデータはパケットロスしても、QUICが再送する必要はありません。また、QUICストリームにも属さないので、送信された順番どおりに並び替えられる必要もありません。ただし、アプリケーション層で再送を要求することはできます。

HTTP/3では、1つのQUICコネクション上で複数のリクエストが送信されています。DATAGRAMフレームはストリームにも属さず単純にアプリケーションデータを運ぶだけですので、どのリクエストに対するものなのかわかりません。そのため、HTTP/3でDATAGRAMフレームを使う場合は、識別用データを付加し、そのDATAGRAMフレームがどのリクエストに紐付く処理なのかを管理します。その具体的な方法は、Using QUIC Datagrams with HTTP/3という仕様で定義されています。

補足情報

「Using QUIC Datagrams with HTTP/3」については、標準化の議論の中で「HTTP Datagrams and the Capsule Protocol」と変更されています。こちらについては、もともとはHTTP/3を前提としたしくみでしたが、HTTP/1.1やHTTP/2で通信を行うプロキシでもDATAGRAMフレームを転送可能にするため再設計されております。

現在の草案は次のリンクから参照できます。

HTTP/3の応用プロトコル ─⁠─ HTTP/3を下位層に用いる

本節では、HTTP/3を利用した応用プロトコルとして、WebTransportとMASQUEを紹介します。これらのプロトコルはHTTPメッセージをやりとりするのではなく、確立したHTTP/3通信上でほかのデータをやりとりすることを目的としています。

なお、これらの仕様は議論中であり、今後大きく変わる可能性があります。

WebTransport ─⁠─ 双方向通信

WebTransportは、WebSocketのようなクライアントとサーバ間の双方向通信においても、QUICやHTTP/3を活用するために登場した技術です。先述のDATAGRAMフレームを活用し、パケットロスしてもアプリケーションデータの再送を必要としない通信が行えます。パケットロスした際に再送されてほしいアプリケーションデータは、QUICストリームで送信します。議論が始まったばかりで、実装としては、GoogleがChromeで実験を進めている段階です。

WebTransportには、JavaScript APIとプロトコルがあります。APIの仕様はW3CのWebTrasnportワーキンググループで、プロトコルの仕様はIETFのWebTransportワーキンググループで、両者連携をとりながら議論が進められています。

API仕様は、ブラウザ内で動作するJavaScriptから通信を開始し、データの送受信を行うAPIが定義されています。これらのAPIを利用することで、WebサイトとしてWebTransportを活用できます。

プロトコル仕様は、HTTP/3上でどのようにWebTransport用の通信を行うかを定義しています。具体的には、WebTransport用のQUICストリームとDATAGRAMフレームの使い方が決められています。

MASQUE ─⁠─ 通信のトンネリング

HTTP/3上で動作し、通信のトンネリングに使えるMASQUEMultiplexed Application Substrate over QUIC EncryptionというしくみがIETFで議論されています。

MASQUEは、HTTP/3通信を確立したあとに、そのQUICコネクション上で別の通信をトンネリングさせることで、安全な通信路であるVPNVirtual Private Networkを確立します。MASQUEクライアントは中継者となるMASQUEプロキシにHTTP/3で接続し、本来の通信先を転送先として指定して通信を行います図1⁠。大きな特徴として、通信を観測する第三者にはただのHTTP/3通信を行っているように見えます。

図1 MASQUE通信
画像

MASQUEは、IETFのMASQUEワーキンググループで議論されています。仕様としては、UDPパケットを転送させるものと、IPパケットを転送させるものなどが議論されています。それぞれ新しく定義したCONNECT-UDPメソッドとCONNECT-IPメソッドを使って、通信の中継のセットアップを行います。

補足情報

最新の草案では、CONNECTメソッドおよび:protocol擬似ヘッダを使う形式に変更されています。

現在の草案は次のリンクから参照できます。

特集のまとめ

本特集では、新しく登場したHTTP/3について見てきました。中でもQUICの仕様を解説した第2章では、QUICがトランスポートプロトコルとしてどのような信頼性を提供するのか、どのように通信の効率化を図るのかを解説しました。HTTP/3の仕様を解説した続く第3章では、受け取ったパケットから処理を行えるというQUICの利点を活かしながら、どのようにHTTPメッセージをやりとりするのかを解説しました。

QUICとHTTP/3は徐々に利用される段階となってきています。利用が広まれば、課題や新しいニーズが生まれることでしょう。第2章のQUICの今後や本章で触れたとおり、すでに議論が始まっているトピックもありますが、きっと新しいトピックも出てきます。

Webとプロトコルの進化はまだまだ続いていきます。興味がある方は、ぜひその動向を追いかけてみてはいかがでしょうか。

おすすめ記事

記事・ニュース一覧