【问题标题】:Click on a dropdown element menu with Selenium Webdriver使用 Selenium Webdriver 单击下拉元素菜单
【发布时间】:2012-09-05 21:21:11
【问题描述】:

我正在尝试自动化管理任务,到目前为止,我已经制作了 selenium 来单击元素以显示下拉菜单。

当需要单击其中一个菜单元素时,我收到一条错误消息,提示必须显示该元素。

代码:

 driver = webdriver.Chrome()
 driver.implicitly_wait(10)
 driver.get(url)
 doc = driver.find_element_by_css_selector('td.ms-vb-title > table')
 try:
    doc.click()
    time.sleep(4)
    menu = driver.find_element_by_xpath('//menu/span[5]')
    time.sleep(4)
    print dir(menu)
    menu.click()
 except:
    traceback.print_exc()
    driver.quit()

错误:

Traceback (most recent call last):
  File "aprobar_docs.py", line 22, in main
    menu.click()
  File "C:\Python27\lib\site-packages\selenium\webdriver\remote\webelement.py",
line 52, in click
    self._execute(Command.CLICK_ELEMENT)
  File "C:\Python27\lib\site-packages\selenium\webdriver\remote\webelement.py",
line 205, in _execute
    return self._parent.execute(command, params)
  File "C:\Python27\lib\site-packages\selenium\webdriver\remote\webdriver.py", l
ine 156, in execute
    self.error_handler.check_response(response)
  File "C:\Python27\lib\site-packages\selenium\webdriver\remote\errorhandler.py"
, line 147, in check_response
    raise exception_class(message, screen, stacktrace)
ElementNotVisibleException: Message: u'Element must be displayed to click'

如您所见,代码要等待很长时间才能加载元素。我也尝试将元素的is_displayed 属性设置为True,但也没有用。

注意:未显示的元素是 xpath 搜索中的元素,它存在是因为我使用 dir(menu) 记录了它

编辑:

menu 变量不是菜单本身,它是作为菜单元素的跨度之一,doc 是被点击以显示下拉列表的 Perfil html 元素。

编辑 2:

在 chrome 工具上检查 DOM,当您单击 doc 时,会在树上创建一个新菜单,我不知道是因为 ajax 调用还是 vanilla js,我不认为这是真的重要的是它是如何创建的。我无法从页面中检索它并从中创建一个 python 对象,它至少没有显示在代码上。

最终编辑:

我最终执行了一些 JavaScript 以使其工作。显然,当 Selenium 找到菜单项时,触发菜单下拉菜单的第一个元素失去焦点并且它使菜单再次不可见,如果您不选择菜单项并等待一段时间菜单下拉菜单仍然显示,如果您尝试从菜单中选择一个元素菜单消失。

【问题讨论】:

  • 你为什么睡在menu元素查找的两边?如果在您检索页面元素时该元素不可见,则无论您等待多长时间,webdriver 都无法单击它。
  • @sr2222 调用 driver.get() 时检索页面,当您执行 doc.click() 时,下拉菜单显示在屏幕上并出现在 dom 树上,我只是消除了这种可能性下拉菜单的加载速度不如执行代码的速度快。菜单元素是存在且可见的,至少对人类来说,我可以保证。
  • 点击后等待菜单显示再次尝试提取doc,对比前后对象的id属性。我偷偷怀疑 selenium 服务器实际上是在您提取第二个元素时引用缓存的 webelement 对象(因为您的点击操作不会触发页面加载事件,所以页面对象不会过时)。
  • 在这种情况下,您确定跨度是可点击的吗?为了可点击,元素必须具有尺寸并且可见。您可能需要单击 span 中的某个元素,而不是 span 本身。
  • @sr2222 <span type="option" text="Eliminar" ...></span>,里面什么都没有。

标签: python selenium automation webdriver selenium-webdriver


【解决方案1】:

你为什么不选择这样的选项

el = driver.find_element_by_id('id_of_select')
for option in el.find_elements_by_tag_name('option'):
    if option.text == 'The Options I Am Looking For':
        option.click() # select() in earlier versions of webdriver

如果您的点击没有触发 ajax 调用来填充您的列表,那么您实际上不需要执行点击。

【讨论】:

  • @Nllesh Sharma 我使用了这种方法,但我收到一个错误,即 Web 元素对象不可迭代。如果它不可迭代,你如何在 for 循环中迭代它
  • @abhi 你确定使用 find_elementSSSSS_by_tag_name() 吗? (只是为了确保你看到了,嘿嘿)
【解决方案2】:

你需要找到目标的链接。您不会真正单击元素,而是单击链接...(或者更确切地说,单击其中包含链接的元素)。话虽如此,点击链接最可靠的方法是隔离链接元素。

frame = driver.find_element_by_id('this_is_your_frame_name') 
links = frame.find_elements_by_xpath('.//a')
links[1].click()

或者,

for link in links:
    if link.text() == "Administratar Permisos":
        link.click()

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2013-08-13
    • 1970-01-01
    • 2014-08-21
    • 2019-02-25
    • 1970-01-01
    • 1970-01-01
    • 2020-04-20
    • 2019-04-18
    相关资源
    最近更新 更多