单击Angular WebPage中的TableRow时出现StaleElementException

时间:2017-06-05 16:39:59

标签: c# angularjs selenium-webdriver protractor-net

<div id="crm" class="row gridrow clickable ng-scope" ng-repeat="customer in customerList" ng-click="gotoRecord(customer.id)">
     <i class="col m1 s1 tiny fa fa-male"></i>
     <div class="col m3 s11 ng-binding"> Allard</div>
     <div class="col m2 s12 ng-binding"></div>
</div>

我有这个HTML片段,它是一行,显示为具有nameCustomer'Allard'的客户的搜索操作。我想点击这个客户继续下一页,但大部分时间都会导致StaleElementException。

我尝试了两种不同的方法,使用Protractor,没有Protractor。

第一种方式:

IWebElement elem = driver.FindElement(By.XPath("//*[contains(text(),'" + nameCustomer + "')]//parent::div[contains(@id,'crm')]"));
        ExplicitWait.WaitAndClick(driver, elem);

第二种方式:

var customers = driver.FindElements(NgBy.Repeater("customer in customerList"));
        foreach (var customer in customers)
        {
            if (elem.Text.Equals(nameCustomer))
            {
                elem.Click();
            }
        }

1 个答案:

答案 0 :(得分:1)

问题(我认为)

使用StaleReferenceExceptions,先前创建的IWebElement不再附加到DOM(您可能已经知道这一点)。最可能发生的是:
1:点击搜索 2:Selenium执行driver.FindElement(...)并找到匹配的元素 3:然后搜索功能完成并且DOM更新。之前找到的旧IWebElement已消失 4:然后 Selenium尝试点击元素(不再存在,导致StaleElementException。有一个元素匹配之前存在的元素,但它&# 39;在Selenium的眼中不是同一个元素。)

你的陈述发生了这种情况&#34;大部分时间&#34; 让我怀疑情况更是如此,因为异常将取决于事件的顺序,这会有所不同取决于Selenium与网页的相对速度。

如何解决(如果这是你的问题)

您需要在页面上找到一些内容,向Selenium表明搜索操作已完成。这就是编写GUI自动化脚本的创造性所在。如果页面上有某些内容,您知道这些内容会因加载而发生变化,请制定明确的等待以确保完成。也许有一个显示的加载栏,或搜索完成时出现的消息。您可以在点击搜索之前获取与您的搜索不匹配的元素,然后明确等待以确保它消失,然后再继续查找您所做的结果期待在那里。

下面会看起来像这样。

# Search action performed before this.
WebDriverWait wait= new WebDriverWait(driver, TimeSpan.FromSeconds(secondsToWait));
wait.Until(ExpectedConditions.InvisibilityOfElementLocated(By.XPath( expressionForElementThatWillDissapear )));


IWebElement elem = driver.FindElement(By.XPath("//*[contains(text(),'" + nameCustomer + "')]//parent::div[contains(@id,'crm')]"));
            ExplicitWait.WaitAndClick(driver, elem);

我建议让方法实现上面的显式等待。这些情况经常会出现。