こんにちは!日々のインフラ運用やWeb開発、本当にお疲れ様です。技術メディア主筆の私です。
突然ですが、みなさんは毎日のように見ているWebサイトの裏側で、ブラウザとサーバーがどんな会話をしているか想像したことはありますか?「URLを入れてページが表示される」という魔法のような体験の裏では、実はものすごい量のデータが、目にも留まらぬ速さで交換されています。
今回は、その通信の主役である「HTTP/2」の世界に一歩踏み込んでみましょう。特に、Webサイトの画像やテキストといった「本当の中身(ペイロード)」を運ぶ『DATAフレーム』の構造と、その断片化の仕組みについて、身近な例えを交えながら優しく紐解いていきたいと思います。
難しい用語が出てきても大丈夫。「一歩ずつ理解していきましょう!」の精神で、一緒に楽しくマスターしていきましょうね。
—
1. HTTP/2ってなぁに?(郵便配達にたとえてみよう)
HTTP/1.1という昔の仕組みでは、Webページを表示するとき、ブラウザはサーバーに対して「この画像ちょうだい!」「次はあのCSSちょうだい!」と、まるで1回ずつ手紙を書いてはポストに投函するようなやり取りをしていました。これだと、前の手紙の返事が返ってくるまで次の手紙が出せなくて、何だかもどかしいですよね。
そこで登場したのがHTTP/2です。HTTP/2は、いわば「巨大な1本の高速道路(コネクション)」の中に、いくつもの「専用レーン(ストリーム)」を通す技術です。
このレーンを行き交う荷物は、すべて「フレーム」という決まったサイズの箱に入れられます。
- 「ヘッダー情報を入れる箱」(HEADERSフレーム)
- 「中身のデータを入れる箱」(DATAフレーム)
今回は、この中の「中身のデータを運ぶ箱」、すなわち『DATAフレーム』にスポットライトを当てていきます!
—
2. DATAフレームの正体:中身のデータを運ぶ「ダンボール箱」
ブラウザが「この画像ファイルが欲しい!」とリクエストを送ると、サーバーは快くその画像データを送り返してくれます。このとき、サーバー側で画像データはバラバラの「バイナリ(0と1のデータ)」に変換され、DATAフレームという名のダンボール箱に詰め込まれます。
実は、HTTP/2のフレームは、どれも共通の「外箱(ヘッダー)」を持っています。この外箱には、以下のような大切な情報が書き記されています。
- 長さ(Length):この箱の中にデータが何バイト入っているか
- タイプ(Type):何の箱か(今回は「DATA」だよ、という目印)
- フラグ(Flags):箱の状態(「これでこの荷物は最後だよ!」といった連絡事項)
- ストリーム識別子(Stream Identifier):どの専用レーンを通っている荷物かを示す番号
難しそうな言葉が並びましたが、要するに「宛先と中身のサイズがしっかり書かれた、安全な宅配便のダンボール箱」だとイメージしてください。
—
3. なぜデータを分割するの?(「最大フレームサイズ」の秘密)
ここで、今回のもう一つの主役である「最大フレームサイズ(SETTINGS_MAX_FRAME_SIZE)」のお話です。
想像してみてください。あなたがAmazonで、幅が3メートルもある巨大なソファを注文したとします。それを普通の軽トラックで運ぼうとしたら…道路のガードレールにぶつかってしまいますよね。他の車の通行も邪魔してしまいます。
ネットワークの世界もまったく同じです。
サーバー側にある「ものすごく大きな画像データや動画ファイル」を、そのままドカンと1つの巨大なDATAフレームに詰めて送ろうとすると、その通信(レーン)をそのデータが独占してしまい、他の大切なデータ(例えば「今すぐ表示してほしい文字情報」など)が通れなくなってしまいます。
これを防ぐために、HTTP/2では「一度に送るダンボール箱の大きさには上限(最大フレームサイズ)を設けましょうね」というルールがあります。これが `SETTINGS_MAX_FRAME_SIZE` です。
断片化(フラグメンテーション)のリアルな挙動
もし送りたいデータが、この最大サイズよりも大きかったらどうなるでしょうか?
答えは簡単。データをいくつもの小さなダンボール箱に分けて(断片化して)、順番に送り出すのです。
例えば、100KBの画像データを送るとしましょう。
もし最大フレームサイズが「16KB(約16,384バイト)」に設定されていたら、サーバーは以下のように振る舞います。
1. 16KB分のデータを詰めた「DATAフレーム1」を送信(まだ続くよ!)
2. 16KB分のデータを詰めた「DATAフレーム2」を送信(まだ続くよ!)
3. …(中略)…
4. 残りのデータを詰めた最後の「DATAフレームN」を送信
このとき、最後の箱には「END_STREAM」という特別なフラグ(スタンプ)が押されます。受け取ったブラウザは、このスタンプを見て「あ、このレーンの荷物はこれで全部揃ったな!よし、画像を組み立てて画面に表示しよう!」と理解するわけです。
—
4. 実務の現場で確認してみよう(設定例とデバッグ)
インフラエンジニアやWebアプリケーションエンジニアとして現場に出ると、この「フレームサイズ」や「データの断片化」を意識する場面に出会います。
例えば、NginxやGo言語のHTTP/2サーバー実装などでは、この最大フレームサイズをチューニングすることができます。以下は、Go言語でHTTP/2サーバーを立てる際の簡単なイメージコードです(雰囲気を感じてみてください)。
package main
import (
“net/http”
“golang.org/x/net/http2”
“golang.org/x/net/http2/h2c”
)
func main() {
handler := http.HandlerFunc(func(w http.ResponseWriter, r http.Request) {
w.Write([]byte(“こんにちは!HTTP/2の世界へようこそ!”))
})
// HTTP/2サーバーの基本設定を行います
h2s := &http2.Server{
// ここで1つのDATAフレームの最大サイズを調整できます
// デフォルトは通常16384バイト(16KB)ですが、環境に合わせて最適化することがあります
MaxUploadBufferPerConnection: 1024 1024, // 1MBなど
}
mux := http.NewServeMux()
mux.Handle(“/”, handler)
// サーバーを起動
server := &http.Server{
Addr: “:8080”,
Handler: h2c.NewHandler(mux, h2s), // 暗号化なしのHTTP/2 (h2c) の例
}
server.ListenAndServe()
}
※実務では、Google Chromeなどのブラウザの「デベロッパーツール(ネットワークタブ)」や、パケット解析ツールである「Wireshark」を使って、実際にどのようなサイズのDATAフレームが流れているかを覗き見ることができます。パケットキャプチャを開いたときに、小さなDATAフレームがパタパタと連続して流れているのを見つけると、ネットワークエンジニアとしては思わずコーヒーを片手にニヤリとしてしまう瞬間です。
—
お疲れ様でした!
HTTP/2におけるDATAフレームの構造と、最大フレームサイズによる断片化の仕組み、なんとなくイメージできましたでしょうか?
- DATAフレームは、Webのデータを運ぶ「ダンボール箱」であること。
- 大きなデータは、ネットワークの渋滞を防ぐために「最大フレームサイズ」の大きさに小分け(断片化)して仲良く運ばれていること。
この2つのポイントさえ押さえておけば、インフラの基礎バッチリです。日々のトラブルシューティングやパフォーマンス改善の引き出しが、また一つ増えましたね。
それでは、次回の技術解説もお楽しみに!快適なネットワークライフを!
コメント