NoSuchElementException,Selenium 无法定位元素

Posted

技术标签:

【中文标题】NoSuchElementException,Selenium 无法定位元素【英文标题】:NoSuchElementException, Selenium unable to locate element 【发布时间】:2018-07-06 09:09:05 【问题描述】:

我想在 selenium 中找到我的 TextField,但我不知道如何(我第一次使用 sellenium)。

我试过了:

 driver.findElement(By.id("originTextField"))

或者通过开发工具中chrome生成的xPath和cssSelector String。

请帮助我,我将不胜感激。

这是html

【问题讨论】:

【参考方案1】:

NoSuchElementException

org.openqa.selenium.NoSuchElementException 俗称 NoSuchElementException 扩展 org.openqa.selenium.NotFoundException,这是 WebDriverException 的一种类型。

NoSuchElementException 可以在以下两种情况下抛出:

使用WebDriver.findElement(By by)时:

//example : WebElement my_element = driver.findElement(By.xpath("//my_xpath"));

使用WebElement.findElement(By by)时:

//example : WebElement my_element = element.findElement(By.xpath("//my_xpath"));

根据 JavaDocs,就像任何其他 WebDriverException 一样,NoSuchElementException 应该包含以下 常量字段

Constant Field      Type                                        Value
SESSION_ID          public static final java.lang.String        "Session ID"
e.g. (Session info: chrome=63.0.3239.108)

DRIVER_INFO         public static final java.lang.String        "Driver info"
e.g. (Driver info: chromedriver=2.34.522940 (1a76f96f66e3ca7b8e57d503b4dd3bccfba87af1),platform=Windows NT 6.1.7601 SP1 x86)

BASE_SUPPORT_URL    protected static final java.lang.String     "http://seleniumhq.org/exceptions/"
e.g. (For documentation on this error, please visit: http://seleniumhq.org/exceptions/no_such_element.html)

原因

NoSuchElementException 的原因可能是以下之一:

您采用的定位器策略没有识别HTML DOM中的任何元素。 您采用的定位器策略无法识别该元素,因为它不在浏览器的Viewport 中。 您采用的 Locator Strategy 标识了元素,但由于存在属性 style="display: none;" 而不可见。 您采用的 Locator Strategy 不能唯一地 识别 HTML DOM 中的所需元素,目前还可以找到其他一些 隐藏 / 不可见 元素。 您尝试定位的 WebElement 位于 <iframe> 标记内。 WebDriver 实例甚至在 HTML DOM 中存在/可见元素之前就开始寻找 WebElement

解决方案

解决NoSuchElementException的解决方案可以是以下任何一种:

采用一个Locator Strategy 唯一标识所需的WebElement。您可以借助开发者工具 (Ctrl+Shift+IF12) 并使用元素检查器

这里有关于how to inspect element in selenium3.6 as firebug is not an option any more for FF 56?的详细讨论

使用executeScript()方法滚动元素查看如下:

WebElement elem = driver.findElement(By.xpath("element_xpath"));
((javascriptExecutor)driver).executeScript("arguments[0].scrollIntoView();", elem);

这里有关于Scrolling to top of the page in Python using Selenium的详细讨论

Incase 元素具有 style="display: none;" 属性,通过executeScript() 方法删除该属性,如下所示:

WebElement element = driver.findElement(By.xpath("element_xpath"));
((JavascriptExecutor)driver).executeScript("arguments[0].removeAttribute('style')", element)
element.sendKeys("text_to_send");

要检查元素是否在<iframe> 内,遍历HTML 以通过以下任一方式定位相应的<iframe> 标记和switchTo() 所需的iframe以下方法:

driver.switchTo().frame("frame_name");
driver.switchTo().frame("frame_id");
driver.switchTo().frame(1); // 1 represents frame index

在这里你可以找到关于Is it possible to switch to an element in a frame without using driver.switchTo().frame(“frameName”) in Selenium Webdriver Java?的详细讨论。

如果元素在 HTML DOM 中不存在/可见,则将WebDriverWait 与ExpectedConditions 设置为正确的方法如下:

等待presenceOfElementLocated

new WebDriverWait(driver, 20).until(ExpectedConditions.presenceOfElementLocated(By.xpath("//div[@class='buttonStyle']//input[@id='originTextField']")));

等待visibilityOfElementLocated

new WebDriverWait(driver, 20).until(ExpectedConditions.visibilityOfElementLocated(By.xpath("//div[@class='buttonStyle']//input[@id='originTextField']")));

等待elementToBeClickable

new WebDriverWait(driver, 20).until(ExpectedConditions.elementToBeClickable(By.xpath("//div[@class='buttonStyle']//input[@id='originTextField']")));

参考

您可以在以下位置找到Selenium 的python 客户端相关讨论:

Selenium “selenium.common.exceptions.NoSuchElementException” when using Chrome

【讨论】:

感谢您的回答,能否为executeScript() 方法提供python 的等效项?谢谢!【参考方案2】:

您的代码是正确的,我怀疑该问题导致您找到该元素时页面未完全加载。

尝试在查找元素之前添加长时间睡眠,如果添加睡眠有效,则将睡眠更改为等待。

代码如下,如果元素不存在则等待10s:

element = WebDriverWait(driver, 10).until(
    EC.presence_of_element_located((By.ID, "originTextField"))
)

【讨论】:

或者你可以输入sleep(1000);然后driver.findElement(By.id("originTextField"))【参考方案3】:

以下代码将帮助您解决问题

wait = new WebDriverWait(driver, 60);
wait.until(ExpectedConditions.presenceOfElementLocated(By.id("originTextField")));

wait = new WebDriverWait(driver, 90);
wait.until(ExpectedConditions.visibilityOf(element)).wait(20);

【讨论】:

以上是关于NoSuchElementException,Selenium 无法定位元素的主要内容,如果未能解决你的问题,请参考以下文章

NoSuchElementException,Selenium 无法定位元素

什么可能导致 NoSuchElementException? [复制]

线程“主”java.util.NoSuchElementException 中的异常:找不到行

文件排序 - 扫描仪 - java.util.NoSuchElementException

访问网页中的列表框时出现 NoSuchElementException

Ubuntu 16.04 上的 DB Visualizer - java.util.NoSuchElementException