6

重複の可能性:
'ab' プログラムは多くのリクエストの後にフリーズします。なぜですか?

簡単なテスト サーバーを次に示します。

require 'rubygems'
require 'rack'
require 'thin'

class HelloWorld

  def call(env)
    [200, {"Content-Type" => "text/plain"}, "OK"]
  end
end

Rack::Handler::Thin.run HelloWorld.new, :Port => 9294 
#I've tried with these added too, 'rack.multithread' => true, 'rack.multiprocess' => true

テスト実行は次のとおりです。

$ ab -n 20000 http://0.0.0.0:9294/sdf
This is ApacheBench, Version 2.3 <$Revision: 655654 $>
Copyright 1996 Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net/
Licensed to The Apache Software Foundation, http://www.apache.org/

Benchmarking 0.0.0.0 (be patient)
Completed 2000 requests
Completed 4000 requests
Completed 6000 requests
Completed 8000 requests
Completed 10000 requests
Completed 12000 requests
Completed 14000 requests
Completed 16000 requests
apr_poll: The timeout specified has expired (70007)
Total of 16347 requests completed

約 16500 で壊れます。なぜですか? どうすれば何が起こっているかを知ることができますか。ruby の GC ですか、それとも OS X マシンで利用可能なネットワーク ソケットの数に関するものですか。MPB 2.5 Ghz 6G メモリを使用しています。


編集

ここで議論し、さまざまなことをテストした結果、net.inet.tcp.msl を 15000 から 1000 ミリ秒に変更すると、ab を使用した高頻度 Web サーバーのテストの問題が解消されるようです。

sudo sysctl -w net.inet.tcp.msl=1000 # this is only good for local development

この問題への回答とともに、参照されている質問を参照してください。'ab' プログラムが多くのリクエストの後にフリーズするのはなぜですか?

4

2 に答える 2

5

わかりやすくするために、ここにソリューションを追加します。OS X で ab を使用して高頻度のテストを実行するための正しい解決策は、'net.inet.tcp.msl' 設定を 15000ms から 1000ms に変更することです。これは、開発ボックスでのみ行う必要があります。

 sudo sysctl -w net.inet.tcp.msl=1000 # this is only good for local development

この回答は、ここのコメントで実行された優れた探偵作業の後に発見され、非常によく似た質問への回答から得られました

于 2012-09-19T07:44:52.693 に答える
2

私はそれを持っていると思います。

abがテストサーバーに接続すると、送信元ポート(たとえば、50134)が開き、宛先ポート(9294)に接続されます。

送信元ポートに対してabが開くポートは、sysctl設定net.inet.ip.portrange.firstおよびnet.inet.ip.portrange.lastによって決定されます。たとえば、私のマシンでは:

philippotter ~ $ sysctl -a | grep ip.portrange
net.inet.ip.portrange.lowfirst: 1023
net.inet.ip.portrange.lowlast: 600
net.inet.ip.portrange.first: 49152
net.inet.ip.portrange.last: 65535
net.inet.ip.portrange.hifirst: 49152
net.inet.ip.portrange.hilast: 65535

これは、abの送信元ポートが49152から65535の範囲になり、合計で16384になることを意味します。

HTTPはTCPプロトコルです。TCP接続が閉じられると、それはTIME_WAIT状態になり、残りの転送中パケットが宛先に到達するのを待ちます。これは、タイムアウトに達するまで、ポートを他の目的に使用できないことを意味します。

したがって、これらすべてをまとめると、abは使用可能なすべてのソースポートを非常に迅速に使い果たします。それらはTIME_WAIT状態になります。再利用することはできません。abはこれ以上接続を作成できません。

ハングしたときにabを強制終了し、再度実行すると、これを確認できます。接続を作成できなくなります。

于 2012-09-16T09:03:49.207 に答える