Селен бегло ждать и пейдж фабрики
Итак, я ломал голову над этим испытанием, пока я не побеждаю. Я был бы очень признателен, если бы кто-нибудь мог мне помочь с этим. Подробности следующим образом.
Ниже приведен пример кода : 1,
1. В примере 1 неверный xpath выглядит так: "// input [@ id = 'identifierIdd']"
2. Это преднамеренно, просто чтобы изучить свободное ожидание. Как и следовало ожидать, через 1 минуту тест завершился и за исключением org.openqa.selenium.NoSuchElementException:
import com.google.common.base.Function;
import org.openqa.selenium.By;
import org.openqa.selenium.NoSuchElementException;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.chrome.ChromeDriver;
import org.openqa.selenium.support.ui.FluentWait;
import org.openqa.selenium.support.ui.Wait;
import static java.util.concurrent.TimeUnit.MINUTES;
import static java.util.concurrent.TimeUnit.SECONDS;
public class Tester01 {
public static void main(String[] args) {
WebDriver webDriver = new ChromeDriver();
webDriver.get("https://accounts.google.com/
signin/v2/identifier?
continue=https%3A%2F%2Fmail.google.com%2Fmail%2F
&service=mail&sacu=1&rip=1&flowName=GlifWebSignIn
&flowEntry=ServiceLogin");
webDriver.manage().window().maximize();
WebElement webElement;
Wait<WebDriver> fluentWaiter = new FluentWait<WebDriver>
(webDriver).withTimeout(1, MINUTES)
.pollingEvery(5, SECONDS)
.withMessage("element couldn't be found after 1 minutes")
.ignoring(NoSuchElementException.class);
webElement = fluentWaiter.until(new Function<WebDriver,
WebElement>()
{
public WebElement apply(WebDriver driver) {
return driver.findElement(By.xpath
("//input[@id='identifierIdd']"));
}
});
webElement.sendKeys("testemail.com");
}
}
- Итак, я решил поэкспериментировать с fluentwait & pageFactory, к сожалению, я не смог понять, как добиться следующей строки из
Tester01
класс с pageFactory.
return driver.findElement(By.xpath("//input[@id='identifierIdd']"));
Детали для беглого ожидания и эксперимента на странице. Ниже приведен пример кода : 2,
import org.openqa.selenium.By; import org.openqa.selenium.support.FindBy; import org.openqa.selenium.support.How; public class LocatorTest{ @FindBy(how = How.XPATH, using="//input[@id='identifierIdd']") public WebElement elementTest; }
А также Tester01
класс с LocatorTest
учебный класс
public class Tester01 {
public static void main(String[] args) {
WebDriver webDriver = new ChromeDriver();
webDriver.get("https://accounts.google.com/signin/v2/identifier?
continue=https%3A%2F%2Fmail.google.
com%2Fmail%2F&service=mail&sacu=1&rip=1
&flowName=GlifWebSignIn&flowEntry=ServiceLogin");
webDriver.manage().window().maximize();
WebElement webElement;
Wait<WebDriver> fluentWaiter = new FluentWait<WebDriver>(webDriver)
.withTimeout(1, MINUTES)
.pollingEvery(5, SECONDS)
.withMessage("element couldn't be found after 1 minutes")
.ignoring(NoSuchElementException.class);
LocatorTest locatorTest = new LocatorTest();
PageFactory.initElements(webDriver, locatorTest);
webElement = fluentWaiter.until
(new Function<WebDriver, WebElement>()
{
public WebElement apply(WebDriver driver) {
return locatorTest.elementTest;
}
});
webElement.sendKeys("testemail.com");
}
}
Так Tester01
класс с pagefactory не ждет в течение 1 минуты, тест немедленно завершается с org.openqa.selenium.NoSuchElementException:
Я думаю, что знаю, в чем проблема, однако, на самом деле не знаю, как преодолеть эту проблему,
Это мое объяснение проблемы, в примере: 2 Tester01
Класс return оператор в экземпляре fluentWaiter не использует соответствующий экземпляр драйвера.
Это линия, о которой я говорю return locatorTest.elementTest;
потому что я думаю, что метод apply() принимает Webdriver
экземпляр однако линия return locatorTest.elementTest;
не использует driver
пример.
Правильно ли мое мышление? Может кто-нибудь, пожалуйста, помогите мне с этим вопросом, пожалуйста? Или предложите альтернативное решение, пожалуйста?
Пожалуйста, дайте мне знать, если что-то из вышеперечисленного не имеет смысла или нужно больше информации.
Заранее спасибо Ниро
1 ответ
PageFactory.initElements()
создаст Proxy
для всех WebElement
а также List<WebElement>
поля. А также настройте стратегии локатора, которые передаются в FindBy
аннотаций. Расположение элементов не выполняется. Это ленивая инициализация. Фактическое местоположение будет сделано, когда такие команды, как click(), sendkeys()
и т. д. отправляются webelement
,
Теперь в первом случае вы ищете фактический элемент
webElement = fluentWaiter.until(new Function<WebDriver,
WebElement>()
{
public WebElement apply(WebDriver driver) {
return driver.findElement(By.xpath
("//input[@id='identifierIdd']"));
}
});
Во втором случае вы просто делаете Java-вызов объекта страницы, который возвращает вам объект Proxy. Никакой селеновый бизнес не задействован.
webElement = fluentWaiter.until
(new Function<WebDriver, WebElement>()
{
public WebElement apply(WebDriver driver) {
return locatorTest.elementTest;
}
});
Но когда этот код запускается - webElement.sendKeys("testemail.com");
фактическое расположение элемента сделано, и это не удается. Здесь не нужно ждать. PageFactory
был инициализирован с webDriver
пример.
Посмотрите на класс [ExpectedConditions], который вы можете использовать вместе с FluentWait или специализированным [WebDriverWait]. Используйте такой метод, как visibilityOf(WebElement) из ExpectedConditions
которые возвращают ExpectedCondition<WebElement>
,
Или вы даже можете посмотреть на LocatorFactory
который ждет определенный период времени при поиске элемента. AjaxElementLocatorFactory и AjaxElementLocator. Хотя это будет излишним, поскольку они предназначены для случаев Ajax, а не для неправильного локатора.