web-dev-qa-db-ja.com

HTTPリバースプロキシは通常、サーバー側ではなく、プロキシ接続のクライアント側でHTTPキープアライブを有効にしますか?

HAProxyには、クライアント側(クライアント<-> HAProxy)でHTTPキープアライブを有効にする機能がありますが、サーバー側(HAProxy <->サーバー)では無効にします。

一部のクライアントは衛星経由でWebサービスに接続しているため、レイテンシは約600ミリ秒です。キープアライブを有効にすると、処理速度が少し向上すると思います。私は正しいですか?

これはNginxでサポートされていますか?これは、他のソフトウェアおよびハードウェアロードバランサーで広く実装されている機能ですか? HAProxy以外に他に何がありますか?

30
LostInComputer

編集:私の回答は、この種のことがロードバランサー/リバースプロキシで一般的なものであるかどうかという、編集されていない元の質問のみを対象としています。 nginx /製品Xがこれをサポートしているかどうかはわかりませんが、リバースプロキシの99.9%はHAproxyを使用した経験です。

正しい。クライアント側ではHTTPキープアライブが、サーバー側ではありません。

どうして?

いくつかの詳細を分解すると、これがメリットである理由がすぐにわかります。この例では、www.example.comというページを読み込んでいて、そのページに3つの画像img [1-3] .jpgが含まれているとします。

キープアライブなしでブラウザがページをロードする

  1. クライアントはポート80でwww.example.comへのTCP接続を確立します
  2. クライアントは "/"のHTTP GETリクエストを行います
  3. サーバーはURI "/"のHTMLコンテンツを送信します(これには3つの画像を参照するHTMLタグが含まれます)
  4. サーバーはTCP接続を閉じます
  5. クライアントはポート80でwww.example.comへのTCP接続を確立します
  6. クライアントは "/img1.jpg"のHTTP GETリクエストを行います
  7. サーバーが画像を送信します
  8. サーバーはTCP接続を閉じます
  9. クライアントはポート80でwww.example.comへのTCP接続を確立します
  10. クライアントは "/img2.jpg"のHTTP GETリクエストを行います
  11. サーバーが画像を送信します
  12. サーバーはTCP接続を閉じます
  13. クライアントはポート80でwww.example.comへのTCP接続を確立します
  14. クライアントは "/img3.jpg"のHTTP GETリクエストを行います
  15. サーバーが画像を送信します
  16. サーバーはTCP接続を閉じます

4つの別々のTCPセッションが確立されてから閉じられていることに注意してください。

ブラウザがキープアライブを使用してページをロードする

HTTPキープアライブを使用すると、単一のTCP接続で複数のHTTPリクエストを次々に処理できます。

  1. クライアントはポート80でwww.example.comへのTCP接続を確立します
  2. クライアントは "/"のHTTP GET要求を行い、サーバーにこれをHTTPキープアライブセッションにするように要求します。
  3. サーバーはURI "/"のHTMLコンテンツを送信します(これには3つの画像を参照するHTMLタグが含まれます)
  4. サーバー閉じない TCP接続
  5. クライアントは「/img1.jpg」のHTTP GETリクエストを行います
  6. サーバーが画像を送信します
  7. クライアントは「/img2.jpg」のHTTP GETリクエストを行います
  8. サーバーが画像を送信します
  9. クライアントは「/img3.jpg」のHTTP GETリクエストを行います
  10. サーバーが画像を送信します
  11. HTTPキープアライブタイムアウト期間内にHTTPリクエストが受信されなくなった場合、サーバーはTCP接続を閉じます

キープアライブでは、1つのTCP接続のみが確立され、最終的に閉じられることに注意してください。

キープアライブが優れているのはなぜですか?

これに答えるには、クライアントとサーバー間のTCP接続を確立するために必要なことを理解する必要があります。これはTCP 3ウェイハンドシェイクと呼ばれます。

  1. クライアントがSYN(クロニーズ)パケットを送信する
  2. サーバーがSYN(クロニズ)ACK(通知)、SYN-ACKを送り返す
  3. クライアントがACK(確認)パケットを送信する
  4. TCP接続がクライアントとサーバーの両方でアクティブと見なされるようになりました

ネットワークにはレイテンシがあるため、3ウェイハンドシェイクの各ステップには一定の時間がかかります。クライアントとサーバーの間に30ミリ秒あるとしましょう。TCP接続の確立に必要なIPパケットの往復送信は、TCP接続の確立に3 x 30ms = 90ミリ秒かかることを意味します。

これはあまり聞こえないかもしれませんが、元の例で4つの個別のTCP接続を確立する必要があると考えると、これは360ミリ秒になります。クライアントとサーバー間の待ち時間が30ミリ秒ではなく100ミリ秒の場合はどうなりますか?次に、4つの接続が確立するのに1200ミリ秒かかります。

さらに悪いことに、一般的なWebページは、ロードするために3つ以上の画像を必要とする場合があり、クライアントが要求する必要のある複数のCSS、JavaScript、画像、またはその他のファイルがある場合があります。ページが他の30個のファイルをロードし、クライアントサーバーの待ち時間が100ミリ秒である場合、TCP接続の確立にどのくらいの時間がかかりますか?

  1. 1 TCP接続を確立するには、レイテンシが3倍、つまり3 x 100ミリ秒= 300ミリ秒かかります。
  2. これは、ページに対して1回、ページで参照される他のファイルごとにさらに30回、31回行う必要があります。 31 x 300ミリ秒= 9.3秒。

他の30個のファイルを参照するWebページをロードするために、TCP接続の確立に9.3秒かかりました。また、HTTPリクエストの送信とレスポンスの受信に費やされた時間も考慮されません。

HTTPキープアライブを使用すると、1つのTCP接続を確立するだけで済みます。これには300ミリ秒かかります。

HTTPキープアライブが非常に優れている場合は、サーバー側でも使用してみませんか?

HTTPリバースプロキシ(HAproxyなど)は通常、プロキシの対象となるバックエンドサーバーの非常に近くに配置されます。ほとんどの場合、リバースプロキシとそのバックエンドサーバー間の遅延は1ミリ秒未満になるため、TCP接続の確立は、クライアント間の接続よりもはるかに高速です。

それは理由の半分だけです。 HTTPサーバーは、クライアント接続ごとに一定量のメモリを割り当てます。キープアライブを使用すると、接続をアライブに維持します。さらに、キープアライブタイムアウトに達するまで、サーバーで一定量のメモリを使用し続けます。これは、サーバーの構成によっては最大15秒になる場合があります。 。

したがって、HTTPリバースプロキシのサーバー側でキープアライブを使用した場合の影響を考慮すると、メモリの必要性が高まりますが、プロキシとサーバー間のレイテンシが非常に低いため、 TCPの3ウェイハンドシェイクにかかる時間の短縮のため、通常、このシナリオでは、プロキシとWebサーバー間のキープアライブを無効にすることをお勧めします。

免責事項:はい、この説明では、通常、ブラウザーがサーバーへの複数のHTTP接続を並行して確立するという事実は考慮されていません。ただし、ブラウザが同じホストに対して行う並列接続の数には制限があり、通常、これはキープアライブを望ましいものにするのに十分なほど小さいです。

44
ThatGraemeGuy

Nginxは両側でキープアライブをサポートしています。

7
VBart