While building test automation for a complex web application using Selenium WebDriver then we face some exception like NoSuchElementException ,ElementNotVisibleException etc.
Problem :-
when the application server or webserver is serving the page too slowly due to resource constraints like :-
- Slow Network
- Slow response from webserver
- Element visible after some time due to Ajax and Javascript.
- Webpage is not loaded properly
Solution:-
where you have to calculate and configure the average wait time your test scripts should wait for WebElements to load on the webpage.We need to use one of the next two approaches: implicit or explicit waits.
There are three ways by which you can make WebDriver wait for WebElement:-
- Implicit wait
- Explicit wait
- Fluent wait
- Synchronizing test using implicit wait
Note :-When webdriver find any element then each time webdriver will wait for a defined amount of time element to visible. Implicit timeout is generic to all the WebElements of a web page.
WebDriver gives an option to set the implicit wait time for all of the operations that the driver does using the manage() method.
Syntax :- driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS);
Lets understand this line of code :-
The Selenium WebDriver provides the Timeouts Interface for configuring the implicit wait. The Timeouts Interface provides an implicitlyWait() method, which accepts the time the driver should wait when searching for an element.
Example:-
- public class ImplicitWaitTime {
- public static void main(String... args) {
- WebDriver driver = new FirefoxDriver();
- driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS);
- driver.get("www.google.com");
- }
- }
2. Synchronizing test using Explicit Wait
The Selenium WebDriver also provides an explicit wait for synchronizing tests, which provides a better control as compared with an implicit wait.
Problem :-
Implicit timeout is generic to all the WebElements of a web page But, if you have one specific WebElement in your application where you want to wait for a very long time, this approach may not work.
Solution:-
So you have to make an exception for only a particular case, like this WebElement. To handle such scenarios, WebDriver has explicit wait time for a WebElement . Explicit wait is an intelligent kind of wait, but it can be applied only for specified elements. Explicit wait gives better options than that of an implicit wait as it will wait for dynamically loaded Ajax elements
.
The Selenium WebDriver provides WebDriverWait and ExpectedCondition classes for implementing an explicit wait
The ExpectedCondition class provides a set of predefined conditions to wait before proceeding further in the code.
The following are the Expected Conditions method that can be used in Explicit Wait:-
- alertIsPresent()
- elementSelectionStateToBe()
- elementToBeClickable()
- elementToBeSelected()
- frameToBeAvaliableAndSwitchToIt()
- invisibilityOfTheElementLocated()
- invisibilityOfElementWithText()
- presenceOfAllElementsLocatedBy()
- presenceOfElementLocated()
- textToBePresentInElement()
- textToBePresentInElementLocated()
- textToBePresentInElementValue()
- titleIs()
- titleContains()
- visibilityOf()
- visibilityOfAllElements()
- visibilityOfAllElementsLocatedBy()
- visibilityOfElementLocated()
Example:-
public void testExplcitWaitTitleContains()
{
//Go to the Google Home Page
WebDriver driver = new FirefoxDriver();
driver.get("http://www.google.com");
//Enter a term to search and submit
WebElement query = driver.findElement(By.name("q"));
query.sendKeys("selenium");
query.click();
//Create Wait using WebDriverWait.
//This will wait for 10 seconds for timeout before title is
//updated with search term
//If title is updated in specified time limit test will move to
//the text step
//instead of waiting for 10 seconds
WebDriverWait wait = new WebDriverWait(driver, 10);
wait.until(ExpectedConditions.titleContains("selenium"));
//Verify Title
assertTrue(driver.getTitle().toLowerCase().
startsWith("selenium"));
driver.quit();
}
3. FluentWait
Fleunt wait is an smart kind of wait, the fluent wait is used to tell the web driver to wait for a condition, as well as the frequency with which we want to check the condition before throwing an "ElementNotVisibleException" exception.
FluentWait instance defines the maximum amount of time to wait for a condition, as well as the frequency with which to check the condition. Furthermore, the user may configure the wait to ignore specific types of exceptions whilst waiting, such as NoSuchElementExceptions when searching for an element on the page.
There are some points were we can use Fluent wait:-
- Frequency: Setting up a repeat cycle with the time frame to verify/check the condition at the regular interval of time Exmaple:-suppose you want to check element in some frequency then we can achieve by using fluent wait
- Whenever we want to ignore some exceptions during running script then we can achieve by using Fluent wait.
Syntax:-
// Waiting 30 seconds for an element to be present on the page, checking
// for its presence once every 5 seconds.
1. Wait<WebDriver> wait = new FluentWait<WebDriver>(driver)
.withTimeout(30, TimeUnit.SECONDS) .
.pollingEvery(5, TimeUnit.SECONDS)
.ignoring(NoSuchElementException.class);
2.WebElement foo = wait.until(new Function<WebDriver, WebElement>()
3.{
4.public WebElement apply(WebDriver driver)
5.{
6.return driver.findElement(By.id("foo"));
7.}
8.}
9.);
Code explanation:-
Line 1: Create Fluent wait instance
Line 2: In Fluent wait class there are some methods we use these methods here like:
- withTimeout(long duration, java.util.concurrent.TimeUnit unit) method is used to Sets how long to wait for the evaluated condition to be true.
- pollingEvery(long duration, java.util.concurrent.TimeUnit unit) method is used to Sets how often the condition should be evaluated.In short we set frequency.
- ignoring(java.lang.Class<? extends java.lang.Throwable> exceptionType) method is used to ignore Expections
Comments
Post a Comment