首页 > 解决方案 > why am I receiving stale element reference on test method?

问题描述

I am currently working on an automation framework using java, selenium, selenium-grid, pageObject with pageFactory.

I am trying to create a method for testing the following html code:

<section class="footer-links">
<div class="footer-layout">
    <ul>
        <li class="title">Header</li>
        <li><a href="/home/">text</a></li>
        <li><a href="/about/">text</a></li>
        <li><a href="/games/">text</a></li>
        <li><a href="/games/download/" >text</a></li>
        <li><a href="/games/mobile/" >text</a></li>
        <li><a href="/events/" >text</a></li>
    </ul>
    <ul>
        <li class="title">Header</li>
        <li><a href="/publishers/" >text</a></li>
        <li><a href="/smth/" target="_blank" >text</a></li>
        <li><a href="/promo/press/" >text</a></li>
    </ul>
    <ul>
        <li class="title">Header</li>
        <li><a href="/support/" >text</a></li>
        <li><a href="/support/payment-inquiries/"  class="loginModalShow" rel="nofollow" >text</a></li>
        <li><a href="/support/general-inquiries/" >text</a></li>
        <li><a href="/support/game-inquiries/"  class="loginModalShow" rel="nofollow" >text</a></li>
    </ul>
    <ul>
        <li class="title">Header</li>
        <li><a href="/blog/" >text</a></li>
        <li><a href="/search/" rel="nofollow" >text</a></li>
        <li><a href="/directory/pc-games/" >text</a></li>
    </ul>
</div>

The code above represents a footer containing 4 lists with some links.

What I am trying to do with the following method is to iterate once through the 4 lists and again inside each list clicking the links and verifying the url to which they redirect against their href attribute value.

@FindBy(css = ".footer-links .footer-layout ul")
public List<WebElement> footerLinksLists;

public void checkFooterLinks(){
    if (footerLinksLists.size()==4){
        for(int i=0; i<footerLinksLists.size(); i++){
            List<WebElement> links =  wait.until(ExpectedConditions.visibilityOfAllElements(footerLinksLists.get(i).findElements(By.cssSelector("li:not(:first-child)")))); // footerLinksLists.get(i).findElements(By.cssSelector("li:not(:first-child)"));
            for (int j=0; j<links.size(); j++) {
                WebElement link = wait.until(ExpectedConditions.elementToBeClickable(links.get(j).findElement(By.cssSelector("a"))));
                String href = link.getAttribute("href");
                link.click();
                if(driver.getCurrentUrl().contains(href)){
                    log.info("Link " + href +" is ok");
                }
                driver.navigate().back();
            }
        }
    }else{
        log.info("the footer does not contain 4 link lists");
    }
}

After starting my test it breaks after entering the for loop with the following error

org.openqa.selenium.StaleElementReferenceException: The element reference of <li> is stale; either the element is no longer attached to the DOM, it is not in the current frame context, or the document has been refreshed

In my test class I have the following code for initializing pageobject containing the method:

WebDriver driver = driverFactory.getDriver();
    WebDriverWait wait = driverFactory.getWait(driver);

homepagePageObject homePage = new homepagePageObject(driver, wait);
    PageFactory.initElements(driver,homePage);
    homePage.createAccount();
    homePage.checkVerifyAccountRibbon();
    homePage.signOut();
    homePage.Login();
    homePage.checkFooterLinks();

Initially I thought it had something to do with waiting for each element but I am receiving the same error after adding the waits/expectedConditions.

Can somebody explain what am I doing wrong and what would be the best solution in this case?

标签: javaseleniumselenium-webdriverpageobjects

解决方案


Because page get refresh and List element lost its value.

You have to manage it By reassign links value.

public void checkFooterLinks(){
    if (footerLinksLists.size()==4){
        for(int i=0; i<footerLinksLists.size(); i++){
            List<WebElement> links =  wait.until(ExpectedConditions.visibilityOfAllElements(footerLinksLists.get(i).findElements(By.cssSelector("li:not(:first-child)")))); // footerLinksLists.get(i).findElements(By.cssSelector("li:not(:first-child)"));
            for (int j=0; j<links.size(); j++) {
                WebElement link = wait.until(ExpectedConditions.elementToBeClickable(links.get(j).findElement(By.cssSelector("a"))));
                String href = link.getAttribute("href");
                link.click();
                if(driver.getCurrentUrl().contains(href)){
                    log.info("Link " + href +" is ok");
                }
                driver.navigate().back();
            }
        links = wait.until(ExpectedConditions.visibilityOfAllElements(footerLinksLists.get(i).findElements(By.cssSelector("li:not(:first-child)"))));
        }
    }else{
        log.info("the footer does not contain 4 link lists");
    }
}

推荐阅读