Waiting strategies in Selenium

Why do we need waits?

Depending on the webpage, certain web elements may be loaded later than the others. The webpage could have a lot of elements such as dropdowns, texts, buttons, images etc. Imagine that an image gets loaded later than web elements.

In such cases, Selenium throws the NoSuchElementException even if our selectors are correct. Java provides the sleep(long milli) method from Thread class. We will have to write Thread.sleep(someTimeInMilliSec) before accessing each and every elements(those taking time to load) throughout our script. It is not advisable to use it in a Selenium script.

Types of waits in Selenium :

Selenium provides both static and dynamic wait strategies. They are known as implicit and explicit waits. Let's learn about them :

Implicit wait :

Implicit wait is a global wait which is applicable to each and every element throughout our script.

driver.manage().timeouts().implicitlyWait(Duration.ofSeconds(20));

The above code means that, we are asking the driver to wait for 20 seconds before finding and executing any commands on all of the elements! It will be applicable for those elements that gets loaded within few milliseconds too. Imagine the time it will take to finish executing a script.!

Explicit wait :

Now, this is something very powerful functionality provided by Selenium. The timeout provided by user will be applicable to web elements as required. That means, if user has provided 20 seconds and elements gets loaded in 5 seconds, the script will NOT wait for the rest of 15 seconds before execution.

WebDriverWait wait = new WebDriverWait(driver, Duration.ofSeconds(20));

WebDriverWait is a class which implements the Wait interface in Selenium. We create the object of the WebDriverWait class which takes the driver and timeout as parameters.

Now, this class has a method until(), that takes an ExpectedConditions parameter which is really helpful. Below are some of the ExpectedConditions :

And there are many more. As per requirement, we can make driver to wait for the element to be visible, clickable, interactable, page url to load, title to load etc.

Fluent Wait :

It is also an explicit/dynamic wait. It implements the Wait interface.

        FluentWait wait = new FluentWait(driver)
                              .withTimeout(Duration.ofSeconds(20))
                              .pollingEvery(Duration.ofSeconds(4));
        wait.until(ExpectedConditions.alertIsPresent());

Using FluentWait, we can provide the explicit polling duration. Polling is how frequently driver will try to find the element.