Селен бегло ждать и пейдж фабрики

Итак, я ломал голову над этим испытанием, пока я не побеждаю. Я был бы очень признателен, если бы кто-нибудь мог мне помочь с этим. Подробности следующим образом.

Ниже приведен пример кода : 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");
    }
    }
  1. Итак, я решил поэкспериментировать с fluentwait & pageFactory, к сожалению, я не смог понять, как добиться следующей строки из Tester01 класс с pageFactory.

return driver.findElement(By.xpath("//input[@id='identifierIdd']"));

  1. Детали для беглого ожидания и эксперимента на странице. Ниже приведен пример кода : 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, а не для неправильного локатора.

Другие вопросы по тегам