From: Robert Klemme Date: 2005-10-21T22:22:11+09:00 Subject: Re: Threads, timing and HTTP Alexander Lamb wrote: > On Oct 21, 2005, at 3:01 PM, Robert Klemme wrote: > >> Alexander Lamb wrote: >> >>> Hello list, >>> >>> I am implementing a very simple script to ping web servers or >>> services (to monitor how our environment is functionning). >>> >>> Some production url's run on more than one host. Therefore, I start >>> a thread for each separate url. >>> >>> The function run in my threads is: >>> >>> def doPing(uri_string, probe) >>> s = uri_string >>> while true >>> begin >>> timeout(@seconds_before_timeout) do |timeout_length| >>> start = Time.new >>> begin >>> open(s) do |result| >>> if result.status[0] != "200" >>> probe.addToLogFile([s,'ERR',0,result.status[1]]) >>> else >>> probe.addToLogFile([s,'OK',Time.new - start,'']) >>> end >>> end >>> rescue Exception >>> probe.addToLogFile([s,'ERR',0,$!]) >>> end >>> end >>> rescue Timeout::Error >>> probe.addToLogFile([s,'ERR',0,'timeout']) >>> end >>> sleep(@seconds_between_ping) >>> end >>> end >>> >>> However, this is a problem. Indeed, I want also to measure the time >>> (round-trip) it takes for the ping (these are only simple pings for >>> the time being). As you can see I get the local time before and >>> after the call. But this doesn't work with threads. Indeed, since >>> the process is shared among threads, the time will be dependent on >>> the number of threads I am running and not a correct view of the >>> actual time it takes to ping. >>> >>> I can't define the piece of code between the two times as critical >>> and only for one thread because if the open-uri blocks, it will >>> prevent another thread to ping another url in the mean time. >>> >>> Any idea? Maybe use processes instead of threads? >>> >> >> Maybe you can exploit one of the result headers. Chances are that >> there >> is a timestamp somewhere. Then you *only* need to synchronize >> clocks on >> your machine and on servers... >> >> Or you switch to a single thread solution. I don't know your ping >> interval but if you don't need to ping too often and don't have too >> many >> servers that should be ok. You can create a simple scheduling that >> always >> picks the URL with the closest ping point... >> >> > I could go single thread (since indeed I am doing a ping per 30 > seconds more or less). However, if the first one I try hangs (until a > timeout for example), I am pushing back the time at which I will ping > the second url. Logically I would need to do something like "ping > each url one after another unless one of them seems to take longer > and then detach a thread to wait for the answer". > For the time being I will test forking a process. You could also have a controller thread that watches your single testing thread. If the testing takes longer than n seconds (where n << timeout) it sets a flag for the current testing thread (with a thread local variable for example) and starts a new tester thread. Cheers robert