Home > Back-end >  How can we pass in an ExpectedConditions as a parameter to wait.until in Selenium Java?
How can we pass in an ExpectedConditions as a parameter to wait.until in Selenium Java?

Time:11-06

I'm finding trouble passing in an ExpectedConditions as a parameter in a method to wait.until(). The wait.until() expects a function to be passed in. I am relatively new to Java, and would appreciate the assistance.

Offending code:

public void waitUntil(WebElement element, long seconds, String errorMessage, ExpectedConditions expectedConditions) {
 if (seconds == 0 || errorMessage.isEmpty()) throw new IllegalArgumentException();
 WebDriverWait wait = new WebDriverWait(driver, Duration.ofSeconds(seconds));
 wait.withMessage(errorMessage);
 // this throws a compiler error.
 wait.until(expectedConditions);
}

wait.until() expects a function to be passed into it, which looks like ExpectedConditions.urlToBe("http://www.test.com").

I am trying to make a method that could be called where any ExpectedCondition i.e. urlToBe, alertIsPresent etc.. could be passed in.

Thank you.

CodePudding user response:

(WebElement element, long seconds, String errorMessage, ExpectedConditions expectedConditions)

In first place, the type of expectedConditions is wrong.

You declared it as ExpectedConditions, which represents the util class.

You actually want ExpectedCondition, the type which all methods from ExpectedConditions returns.

But just changing it to ExpectedCondition is not enough. Because you will receive an warning about Raw type, because ExpectedCondition is a generic class.

So you have to declare the type parameter of class, and because you want to include everything, you use wildcard ?

In the final, the parameter should be ExpectedCondition<?> expectedConditions

CodePudding user response:

WebDriverWait has a constructor that is overloaded to take long as a second args. You do not need to use Duration.ofSeconds(seconds)

Also,

The method until(Function<? super WebDriver,V>) in the type FluentWait<WebDriver> is not applicable for the arguments (ExpectedConditions)

Fix :

You should use expectedConditions with one the conjunction like

  1. elementToBeClickable
  2. visibilityOfElement

and so on..

Code :

public void waitUntil(WebElement element, long seconds, String errorMessage, ExpectedConditions expectedConditions) {
     if (seconds == 0 || errorMessage.isEmpty()) throw new IllegalArgumentException();
     WebDriverWait wait = new WebDriverWait(driver, seconds);
     wait.withMessage(errorMessage);
     WebElement elemenet  = wait.until(expectedConditions.elementToBeClickable(By.xpath("//some xpath")));
    }

Internal overloaded method :

  */
  public WebDriverWait(WebDriver driver, long timeOutInSeconds) {
    this(
        driver,
        java.time.Clock.systemDefaultZone(),
        Sleeper.SYSTEM_SLEEPER,
        timeOutInSeconds,
        DEFAULT_SLEEP_TIMEOUT);
  }

CodePudding user response:

I don't see anythin wrong in your code block. However you need to ensure a couple of things as follows:

  • Whhile using ExpectedConditions you have to make the following import:

    import org.openqa.selenium.support.ui.ExpectedConditions;
    
  • As you are using Selenium 4.0.0 you need to use guava-31.0.1-jre.jar

  • Related