96

したがって、httpについて1つか2つのことを知っているhaproxyの作者によると:

Keep-aliveは、CPUが100倍遅いときにサーバーのCPU使用率を減らすために発明されました。しかし、言われていないことは、持続的接続は、それらを開いたクライアント以外の誰もが使用できない間、多くのメモリを消費するということです。現在、2009年のCPUは非常に安価であり、メモリはアーキテクチャまたは価格によって数ギガバイトに制限されています。サイトが存続する必要がある場合、実際の問題があります。負荷の高いサイトでは、最大数の同時クライアントをサポートするために、キープアライブが無効になることがよくあります。キープアライブがないことの本当の欠点は、オブジェクトをフェッチするための待ち時間がわずかに長くなることです。ブラウザは、これを補うために、キープアライブ以外のサイトでの同時接続の数を2倍にします。

http://haproxy.1wt.eu/から)

これは他の人々の経験と一致していますか?つまり、キープアライブなしで-結果は今ではほとんど目立たないのですか?(WebSocketなどでは、非常に応答性の高いアプリの場合、キープアライブステータスに関係なく接続が「開いた」状態に保たれることに注意してください)。サーバーから離れている人にとって、またはページをロードするときに同じホストからロードするアーティファクトが多数ある場合、その効果は大きくなりますか?(CSS、画像、JSなどはキャッシュフレンドリーなCDNからますます増えていると思います)。

考え?

(これがserverfault.comのものであるかどうかはわかりませんが、誰かがそこに移動するように指示するまで、クロスポストはしません)。

4

4 に答える 4

146

ねえ、私はこの引用の著者なので、返答します:-)

大規模なサイトには、同時接続と遅延という2つの大きな問題があります。同時接続は、コンテンツのダウンロードに時間がかかる低速のクライアントと、アイドル状態の接続状態が原因で発生します。これらのアイドル状態の接続状態は、キープアライブと呼ばれる複数のオブジェクトをフェッチするための接続の再利用によって発生します。これは、遅延によってさらに増加し​​ます。クライアントがサーバーに非常に近い場合、接続を集中的に使用して、アイドル状態になることはほとんどありません。ただし、シーケンスが終了すると、誰もチャネルをすばやく閉じることを気にせず、接続は開いたままで、長期間使用されません。これが、多くの人が非常に低いキープアライブタイムアウトの使用を提案する理由です。Apacheなどの一部のサーバーでは、設定できる最小のタイムアウトは1秒であり、多くの場合、高負荷に耐えるには長すぎます。目の前に20000のクライアントがあり、それらが平均して毎秒1つのオブジェクトをフェッチする場合、それらの20000の接続が永続的に確立されます。Apacheのような汎用サーバーでの20000の同時接続は巨大であり、ロードされるモジュールに応じて32〜64 GBのRAMが必要になり、RAMを追加してもそれほど高くなることはおそらく期待できません。実際には、20000クライアントの場合、ブラウザにフェッチするオブジェクトが多数ある場合、ブラウザは2〜3の接続を設定しようとするため、サーバー上に40000〜60000の同時接続が表示されることもあります。また、RAMを追加しても、これ以上高くなることはおそらく期待できません。実際には、20000クライアントの場合、ブラウザにフェッチするオブジェクトが多数ある場合、ブラウザは2〜3の接続を設定しようとするため、サーバー上に40000〜60000の同時接続が表示されることもあります。また、RAMを追加しても、これ以上高くなることはおそらく期待できません。実際には、20000クライアントの場合、ブラウザにフェッチするオブジェクトが多数ある場合、ブラウザは2〜3の接続を設定しようとするため、サーバー上に40000〜60000の同時接続が表示されることもあります。

各オブジェクトの後で接続を閉じると、同時接続の数が大幅に減少します。実際、オブジェクト間の時間までにオブジェクトをダウンロードする平均時間に対応する係数で低下します。オブジェクト(ミニチュア写真、ボタンなど)をダウンロードするのに50ミリ秒必要で、上記のように1秒あたり平均1つのオブジェクトをダウンロードする場合、クライアントあたりの接続数は0.05、つまり1000になります。 20000クライアントの同時接続。

これで、新しい接続を確立する時間が重要になります。遠く離れたクライアントでは、不快な遅延が発生します。以前は、キープアライブが無効になっていると、ブラウザは大量の同時接続を使用していました。MSIEでは4、Netscapeでは8の数字を覚えています。これは、実際には、オブジェクトごとの平均レイテンシをその分で割ったものになります。キープアライブがどこにでも存在するようになった今、リモートサーバーの負荷がさらに増加し​​、ブラウザがインターネットのインフラストラクチャの保護を処理するため、それほど多くの数は見られなくなりました。

これは、今日のブラウザでは、非キープアライブサービスをキープアライブサービスと同じくらい応答性の高いものにするのが難しいことを意味します。また、一部のブラウザ(例:Opera)は、ヒューリスティックを使用してパイプラインを使用しようとします。パイプライン処理は、応答を待たずに複数の要求を送信することでレイテンシーをほぼ排除するため、keep-aliveを使用する効率的な方法です。100枚の小さな写真があるページで試してみましたが、最初のアクセスはキープアライブなしの約2倍の速さですが、応答が非常に小さいため遅延のみがカウントされるため、次のアクセスは約8倍の速さです( 「304」応答)。

理想的には、ブラウザにいくつかの調整機能を設定して、フェッチされたオブジェクト間の接続を維持し、ページが完成したらすぐに削除する必要があると思います。しかし、残念ながらそれは見られません。

このため、Apacheなどの汎用サーバーをフロントサイドにインストールする必要があり、大量のクライアントをサポートする必要がある一部のサイトでは、通常、キープアライブを無効にする必要があります。また、ブラウザに接続数を増やすように強制するために、ダウンロードを並列化できるように複数のドメイン名を使用します。SSLを集中的に使用しているサイトでは、ラウンドトリップが1回追加されるため、接続設定がさらに高くなるため、特に問題が発生します。

最近より一般的に観察されているのは、そのようなサイトはhaproxyやnginxなどの軽いフロントエンドをインストールすることを好むということです。これらは数万から数十万の同時接続を問題なく処理し、クライアント側でキープアライブを有効にし、 Apache側。この面では、接続を確立するためのコストはCPUの観点からはほとんどゼロであり、時間の観点からはまったく目立ちません。このようにして、これは両方の長所を提供します。クライアント側でのタイムアウトが非常に少なく、サーバー側での接続数が少ない、維持による待ち時間が短いことです。みんなが幸せだ :-)

一部の商用製品は、フロントロードバランサーとサーバー間の接続を再利用し、それらを介してすべてのクライアント接続を多重化することにより、これをさらに改善します。サーバーがLBに近い場合、ゲインは以前のソリューションよりもそれほど高くはありませんが、複数のユーザー間で予期しない接続の共有が原因でユーザー間でセッションが交差するリスクがないように、アプリケーションを調整する必要があります。 。理論的には、これは決して起こらないはずです。現実は大きく異なります:-)

于 2010-11-10T06:49:17.247 に答える
23

これが書かれてから(そしてここにstackoverflowに投稿されてから)、今では人気が高まっているnginxなどのサーバーがあります。

たとえば、nginxは、わずか2.5 MB(メガバイト)のRAMを使用して、単一のプロセスで10,000のキープアライブ接続を開いたままにすることができます。実際、RAMが非常に少ない状態で数千の接続を開いたままにしておくのは簡単です。また、開くファイルハンドルやTCP接続の数など、他の制限にぶつかるだけです。

キープアライブは、キープアライブ仕様自体の問題ではなく、Apacheのプロセスベースのスケーリングモデルと、それに対応するようにアーキテクチャが設計されていないサーバーにハッキングされたキープアライブの問題でした。

特に問題となるのは、Apache Prefork + mod_php+keep-alivesです。これは、PHPプロセスが完全にアイドル状態であり、キープアライブとしてのみ開いたままであっても、すべての接続がPHPプロセスが占有するすべてのRAMを占有し続けるモデルです。これはスケーラブルではありません。ただし、サーバーをこのように設計する必要はありません。サーバーがすべてのキープアライブ接続を個別のプロセスに保持する必要がある特別な理由はありません(特に、そのようなすべてのプロセスに完全なPHPインタープリターがある場合はそうではありません)。PHP-FPMとnginxのようなイベントベースのサーバー処理モデルは、問題をエレガントに解決します。

2015年の更新:

SPDYとHTTP/2は、HTTPのキープアライブ機能をさらに優れたものに置き換えます。接続を維持して複数の要求と応答を行うだけでなく、それらを多重化して、応答を任意の順序で送信できるようにする機能です。 、および並行して、要求された順序だけでなく。これにより、遅い応答が速い応答をブロックするのを防ぎ、ブラウザが単一のサーバーへの複数の並列接続を開いたままにしておきたいという誘惑を取り除きます。これらのテクノロジーは、mod_phpアプローチの不備と、PHP-FPMのようなものと個別に結合されたイベントベース(または少なくともマルチスレッド)のWebサーバーのようなものの利点をさらに強調しています。

于 2013-12-26T06:27:47.293 に答える
2

私の理解では、それはCPUとはほとんど関係がありませんでしたが、世界の反対側に繰り返しソケットを開く際の待ち時間です。帯域幅が無限であっても、接続の待ち時間によってプロセス全体の速度が低下します。ページに数十のオブジェクトがある場合は増幅されます。持続的接続でも要求/応答の待ち時間がありますが、平均して2つのソケットがある場合は、一方がデータをストリーミングし、もう一方がブロックしている可能性があるため、その待ち時間は短くなります。また、ルーターは、ソケットに書き込む前にソケットが接続されていると想定することはありません。フルラウンドトリップハンドシェイクが必要です。繰り返しますが、私は専門家であるとは主張していませんが、これは私がいつもそれを見た方法です。本当にクールなのは、完全にASYNCのプロトコルです(いいえ、完全に病気のプロトコルではありません)。

于 2010-11-09T22:50:53.213 に答える
2

CloudFrontやCloudFlareなどの「オリジンプル」CDNを使用している場合は、非常に長いキープアライブが役立ちます。実際、完全に動的なコンテンツを提供している場合でも、これはCDNがない場合よりも高速になる可能性があります。

各PoPが基本的にサーバーに永続的に接続するように長期間存続している場合、ユーザーが初めてサイトにアクセスすると、ローカルPoPとの低速ハンドシェイクではなく、高速TCPハンドシェイクを実行できます。(ライト自体は、ファイバーを介して世界の半分を移動するのに約100ミリ秒かかります。また、TCP接続を確立するには、3つのパケットを やり取りする必要があります。SSLには3つのラウンドトリップが必要です。)

于 2013-04-11T14:25:19.743 に答える