Skip to content
Advertisement

Selenium – select an input from an angularjs component

<md-datepicker ng-model="mc.date.from" required="" md-val="">
  <span class="input-group date" style="width:144px">
    <input size="16" type="text"
           class="form-control"
           autocomplete="off">
    <span class="input-group-btn">
    <button class="btn btn-default" tabindex="-1" >
      <i class="glyphicon glyphicon-calendar"></i>
    </button>
    </span>
  </span>
</md-datepicker>

I have an AngularJs component that contains an input of type text. I have used the following code to enter a date. It fails most of the times when I run the test headless.

WebElement fromDate = driver.findElement(
    By.tagName("md-datepicker"))
    .findElement(By.tagName("input"));

if (fromDate.getAttribute("value").length() > 0) {
    fromDate.clear();
}
fromDate.sendKeys(startDate);

There are a few other inputs before the datepicker that I fill in. But when the test reaches datepciker, it fails because it can not find it.

How can to fix this issue?

Update

I have used this method right before the above code.

public static void waitUntilVisible(By locator) {
    final long startTime = System.currentTimeMillis();
    final Duration duration = Duration.ofSeconds(2);
    Wait<WebDriver> wait = new FluentWait<WebDriver>(driver)
        .pollingEvery(duration)
        .ignoring(StaleElementReferenceException.class);

    while ((System.currentTimeMillis() - startTime) < 91000) {
        try {
            wait.until(ExpectedConditions.presenceOfElementLocated(locator));
            break;
        } catch (StaleElementReferenceException e) {
            log.info("", e);
        }
    }
}

Advertisement

Answer

I could only solve this problem with a try a catch block where I catch StaleElementReferenceException.

   WebElement input;
    try {
        input = driver.findElement(
            By.tagName("md-datepicker"))
            .findElement(By.tagName("input"));

    } catch(StaleElementReferenceException e) {
        input = driver.findElement(By.xpath("//md-datepicker/span/input"));
    }

    if (input.getAttribute("value").length() > 0) {
        input.clear();
    }

As I have stated in the question, I use waitUntilVisible method to wait for the presence of the input.


I asked this question on 29th October 2018. At the time, I was using selenium version 3.14.0. But this approach selects the input neither should you use selenium version 3.141.0.


Update 30 september 2021

Wait until element to be clickable.

    public WebElement getElementWhenClickable(By selector) {
        return new WebDriverWait(driver, 60)
                .ignoring(StaleElementReferenceException.class)
                .until(ExpectedConditions.elementToBeClickable(selector));
    }

Find its nearest unique parent.

WebElement parent = getElementWhenClickable(By.cssSelector("#parent"))

Find the input

WebElement input = parent.findElement(By.cssSelector("md-datepicker[ng-model="mc.date.from"] input"))

5 People found this is helpful
Advertisement