我正在抓取一个网站www.lipperleaders.com。我想提取新加坡的资金细节。我已成功实施下拉选择,并提取了提交选项后出现的第一页的内容。但是当我尝试转到下一页(通过使代码单击下一个按钮)时,我收到错误'Element is no longer attached to the DOM'
。
我的代码大约有100行,但我可以大致了解代码的执行流程:
... # creating driver object and all the imports
def main():
...
result = find_elements_by_tag_name('span')
...
driver.find_element_by_id("ctl00_ContentPlaceHolder1_ucDataPager_btnNext").click()
main()
main()
此代码适用于第1页但在单击下一个按钮后再次调用main()
时。在这个递归方法之前,我也试过把它放在一个循环中,然后也是同样的错误。
如果我写相同的代码,如:
# some code
result = find_elements_by_tag_name('span')
driver.find_element_by_id("ctl00_ContentPlaceHolder1_ucDataPager_btnNext").click()
# some code
driver.find_element_by_id("ctl00_ContentPlaceHolder1_ucDataPager_btnNext").click()
.
.
此代码可以很好地处理下一页加载的任何错误,并执行之后编写的代码。但我不能为500页写相同的driver.find_element_by_id().click()
,即使我必须重复与每页相关的其余代码。这就是为什么我尝试循环或递归,但它不适合我。
请让我知道我的方法有什么问题。
答案 0 :(得分:7)
问题是该元素被某些javascript分离。因此,您应该让驱动程序等待元素:这可以通过设置implicitly_wait
来完成,请参阅:
from selenium import webdriver
ff = webdriver.Firefox()
ff.implicitly_wait(10) # seconds
...
myDynamicElement = ff.find_element_by_id("myDynamicElement")
这 http://docs.seleniumhq.org/docs/04_webdriver_advanced.jsp#implicit-waits
答案 1 :(得分:1)
看起来这是一个陈旧的元素异常,通常在你试图找到一些元素时会发生。 Which gets loaded every time but you found it earlier
,所以这是陈旧的。
我建议使用一些自定义方法来避免这种情况,这是最简单的解决方案之一:
void clickOnStaleElement(String id, WebDriver driver) {
try {
driver.find_element_by_id(id).click();
} catch (StaleElementReferenceException e) {
// Trying to find element stale element
clickOnStaleElement(id, driver);
} catch (NoSuchElementException ele) {
clickOnStaleElement(id, driver);
}
}