Proper Use of the Sleep Method in Automation

zzz

Very often I see automators using the sleep method in their Web browser automation scripts. This makes me cringe and sigh (a heavy sigh that is). Improper use of the sleep method is simply a bad idea.


For example, take the following pseudo-code:


link.click( )
sleep(30 seconds) #waiting for flaky frame to load
verify.html(“My text in frame”)


Siiiigh… This pattern plain sucks. For two reasons in particular:



  1. If the page loads in 1 second, you just wasted 29 seconds.
  2. If the page loads in 31 seconds, your script just broke, or the test failed.

From my personal experience, people typically write this evil code because:



  1. The way the automation library ties into the browsers “the page has completed loading” events are unreliable so they are left with sleep to ensure the page is really there before testing continues.
  2. They’re in a hurry, debugging takes too long, and providing an average sleep fixes the issue (temporarily) 

I’d like to help you out with #1; I’ll leave #2 up to you.


When detection of completion events isn’t reliable within a framework, you need to come up with your own type of detection. What you’re left with when the “the page has completed loading” event has come and gone is verification of object(s) on the page to see if the page is there. However you can’t just sleep and then verify, instead of sleep I recommend a power nap instead. A power nap method could like this: 


powerNap(time sleepTime, HTMLobject objectToWaitForName)
{
    NapTimeStart = Time.now

    while not (HTMLobject.exists)
    (
        TimeGoneBy = Time.now – NapTimeStart

        if (TimeGoneBy >= sleepTime )
        (
            break
         )
         else
        (
            sleep(1 second)
         )
    )
}


With this loop you will only waste a maximum of 1 second once your HTML object is actually found on the page. Your automation code/test could then look something like this:


link.click( )
powerNap(30 seconds, lastObjectThatLoadsOnThePage )
verify.html(“blahblah”)


Now this method isn’t guaranteed to work, however your success % is going to go up dramatically. The caveat to this approach is the fact that just because the HTML object exists doesn’t mean the entire page is there. If you are attempting to do something with that object and it relies on other objects that aren’t loaded yet, then you might get an error (e.g. click a link that has a reference to a method in a .js include file that isn’t fully loaded yet). To avoid this you’ll want to pick an object that you know loads last for the page and sometimes that can be tricky. You have to play with it a bit, but if you put the time in now, you’ll get rid of those wasteful and sometimes test breaking sleeps.


As an added bonus you could take the example method provided and go one step further to wait for multiple HTML objects to be present before moving on. With a method like that you could verify the existence of several HTML objects on the page without using assert or verify methods (much like SWExplorerAutomation’s Scene object).


In summary, without looping use the sleep method for debugging and nothing more, instead of sleep take a powerNap.

One Response to Proper Use of the Sleep Method in Automation

  1. Watir has a command for this pattern:

    wait_until {html_object.exists?}

    This does everything you mention in your method here plus it will also raise an exception (rather than simply return) if the timeout has been raised, which helps with debugging test failures.

    Indeed, one of the great things about Ruby is that you can also use this method to verify multiple objects, as you suggest:

    wait_until {object1.exists? && object2.exists?}

Leave a Reply

Your email address will not be published. Required fields are marked *