甚至当我使用`FluentWait<>`时,StaleElementReferenceException [英] StaleElementReferenceException even when I use `FluentWait<>`

查看:148
本文介绍了甚至当我使用`FluentWait<>`时,StaleElementReferenceException的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述



我的测试失败偶尔使用使用remoteWebDriver时(从未使用local-webDriver失败)

 然后,预览HTML中的横幅图像应为p_1047_o_9075_banner_1423040308.png


失败
org.openqa.selenium.StaleElementReferenceException:陈旧元素引用:元素未附加到页面文档

我认为当我将我的代码重构为这个时,我已经绕过了这个异常:

  public String getSrcAfterWait(final By){
WebElement webElement = getElementAfterWaitForDisplay2(by);
String currentSrc = null;
if(webElement!= null){
currentSrc = webElement.getAttribute(src);
}
return currentSrc;
}


public WebElement getElementAfterWaitForDisplay2(final By){
Wait< WebDriver> wait = new FluentWait<>(driver)
.withTimeout(30,TimeUnit.SECONDS)
.pollingEvery(5,TimeUnit.SECONDS)
.ignoring(NoSuchElementException.class,StaleElementReferenceException.class );

return wait.until(ExpectedConditions.presenceOfElementLocated(by));
}

如何进一步稳定这项测试?

更新



我在尝试 mentallurg 解决方案。但这是否结构良好?

  public String getButtonTextAfterWait(final By){
String currentText;
尝试{
currentText = tryToGetText(by);
$ b $ catch(StaleElementReferenceException ex)
{
currentText = tryToGetText(by);
}
返回currentText;

$ / code $ <$ $ p

解决方案

可能会发生以下情况。

场景1.
在getSrcAfterWait方法中,您使用getElementAfterWaitForDisplay2定位元素。但在调用webElement.getAttribute(src)之前,元素会在页面上发生变化。当你调用webElement.getAttribute(src)时,webElement指向一个已经过时的(不是更多的)元素。这导致了StaleElementReferenceException。

场景2.
也许你有某种动画。所以定期创建一个新的元素实例很多次。 getElementAfterWaitForDisplay2总是为By条件找到一个元素,但时间到了它是页面上的一个新对象。在找到元素之后,在调用webElement.getAttribute(src)之前,在页面上(在DOM中)创建了一个新实例。因此,您定位的变量引用已经过时的实例。

这两种情况下的简单解决方案:捕获异常并再次找到对象。



更复杂的解决方案,但更通用:使用代理对象并实现异常处理和定位。


I run web E2E tests (using cucumber, junit, selenium webDriver) on Ubunto.

my test fails sporadically when using remoteWebDriver (never fails with local-webDriver)

Then banner image in preview html should be "p_1047_o_9075_banner_1423040308.png"


Failure 
org.openqa.selenium.StaleElementReferenceException: stale element reference: element is not attached to the page document

I thought I have bypassed this exception when I refactored my code to this:

    public String getSrcAfterWait(final By by) {
        WebElement webElement = getElementAfterWaitForDisplay2(by);
        String currentSrc = null;
        if (webElement != null) {
            currentSrc = webElement.getAttribute("src");
        }
        return currentSrc;
    }


 public WebElement getElementAfterWaitForDisplay2(final By by) {
        Wait<WebDriver> wait = new FluentWait<>(driver)
                .withTimeout(30, TimeUnit.SECONDS)
                .pollingEvery(5, TimeUnit.SECONDS)
                .ignoring(NoSuchElementException.class, StaleElementReferenceException.class);

        return wait.until(ExpectedConditions.presenceOfElementLocated(by));
    }

how can i stabilize this test further?

Update

I'm trying mentallurg solution. But is this well structured?

  public String getButtonTextAfterWait(final By by) {
        String currentText;
        try {
            currentText = tryToGetText(by);

        } catch (StaleElementReferenceException ex)
        {
            currentText = tryToGetText(by);
        }
        return currentText;
    }

解决方案

If you page is dynamic, following can happen.

Scenario 1. In the method "getSrcAfterWait", you located the element with "getElementAfterWaitForDisplay2". But before you call webElement.getAttribute("src"), the element changes on the page. And when you call webElement.getAttribute("src"), the "webElement" points to an already obsolete (not more existing) element. This leads to StaleElementReferenceException.

Scenario 2. May be you have some kind of animation. So that periodically a new instance of element is create many times. The "getElementAfterWaitForDisplay2" always find an element for "By" condition, but time to time it is a newer object on the page. After you located the element and before you call webElement.getAttribute("src") there was a new instance created on the page (in the DOM). So that your located variable refers to the already obsolete instance.

The simple solution in both cases: catch the exception and locate the object again.

More complex solution, but more generic: use proxy objects and implement exception handling and locating there.

这篇关于甚至当我使用`FluentWait&lt;&gt;`时,StaleElementReferenceException的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆