【问题标题】:Unable to make my script wait conditionally无法让我的脚本有条件地等待
【发布时间】:2019-07-03 12:23:39
【问题描述】:

我尝试在 python 中结合 selenium 编写一个脚本来等待某个元素可用。我希望我的脚本等待的内容受验证码保护。我不想设置固定时间。所以,我需要它等到我自己解决。

我试过这样:

import time
from selenium import webdriver

URL = "https://www.someurl.com/"

driver = webdriver.Chrome()
driver.get(URL)
while not driver.find_element_by_css_selector(".listing-content"):
    time.sleep(1)

print(driver.current_url)
driver.quit()

但是,脚本抛出错误:

selenium.common.exceptions.NoSuchElementException: Message: no such element: Unable to locate element:

我怎样才能让我的脚本等到元素可用,无论需要多长时间?

【问题讨论】:

  • 您是否尝试在 while 循环内的 try/except 块中运行 find_elment_by_css_selector 函数?
  • 您可以在验证码存在时循环播放吗?
  • 是的,我尝试过这种方式@QHarr。一旦我解决了该验证码,该脚本就会引发错误,因为该 while 循环不再存在,并且这一行 driver.find_element_by_css_selector(".listing-content") 引发了相同的错误(考虑选择器包含验证码元素)。
  • 在 try 块中是否相同?
  • 我无法以正确的方式组织该 try/except 块。 try/except 块如何无限期运行?

标签: python python-3.x selenium selenium-webdriver web-scraping


【解决方案1】:

如果您不想硬编码等待时间,可以使用 ExplicitWait 和 float("inf"),在 Python 中代表 INFINITY

from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait as wait
from selenium.webdriver.support import expected_conditions as EC

wait(driver, float("inf")).until(EC.presence_of_element_located((By.CLASS_NAME, "listing-content")))

【讨论】:

    【解决方案2】:

    正如您询问如何组织 try/except 块,这里有一个想法。不过,我建议坚持使用 inf-wait 方法。

    while True:
        try:
            driver.find_element_by_css_selector(".listing-content")
            break
        except:
            time.sleep(0.1)
    

    我会包含 time.sleep() 语句以最小化您的函数调用次数。

    【讨论】:

    • if ret: 在这里是多余的:break 只有在ret = driver.find_element_by_css_selector(".listing-content") 没有引发异常时才会被执行
    【解决方案3】:

    你应该使用 WebDriverWait:

    from selenium.webdriver.common.by import By
    from selenium.webdriver.support.ui import WebDriverWait
    from selenium.webdriver.support import expected_conditions as EC
    ...
    
    element = WebDriverWait(driver, 10000).until(EC.presence_of_element_located((By.CSS_SELECTOR, ".listing-content")))
    

    它不会无限期地等待,但您可以将超时设置为高。否则,您可以尝试在循环中使用 WebDriverWait 语句。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-03-22
      • 2020-05-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-01-15
      相关资源
      最近更新 更多