元素当前不可见,因此可能无法与之交互,Selenium Dropdown Box Python
Posted
技术标签:
【中文标题】元素当前不可见,因此可能无法与之交互,Selenium Dropdown Box Python【英文标题】:Element is not currently visible and so may not be interacted with, Selenium Dropdown Box Python 【发布时间】:2016-04-30 23:29:15 【问题描述】:我需要浏览我网页上的所有页面。所有这些页面的左上角都有一个下拉框,其中包含所有可用的城市。我想通过选择此下拉框中的每个位置来访问每个页面。下拉框有一个滚动条,当我想选择它下面的选项时,它会给我异常消息:
Message: Element is not currently visible and so may not be interacted with
Stacktrace:
at fxdriver.preconditions.visible (file:///tmp/tmpHWLMyH/extensions/fxdriver@googlecode.com/components/command-processor.js:9981)
at DelayedCommand.prototype.checkPreconditions_ (file:///tmp/tmpHWLMyH/extensions/fxdriver@googlecode.com/components/command-processor.js:12517)
at DelayedCommand.prototype.executeInternal_/h (file:///tmp/tmpHWLMyH/extensions/fxdriver@googlecode.com/components/command-processor.js:12534)
at DelayedCommand.prototype.executeInternal_ (file:///tmp/tmpHWLMyH/extensions/fxdriver@googlecode.com/components/command-processor.js:12539)
at DelayedCommand.prototype.execute/< (file:///tmp/tmpHWLMyH/extensions/fxdriver@googlecode.com/components/command-processor.js:12481)
代码如下:
#!/bin/env/python
# -*- coding: utf-8 -*-
import time
from selenium.webdriver.common.by import By
from selenium.webdriver.support.wait import WebDriverWait
from selenium import webdriver
from selenium.common.exceptions import NoSuchElementException
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import Select
def get_browser():
return webdriver.Firefox()
main_page_url = "http://example.com/"
basic_url = 'http://example.com/ogloszenia-kobiet.html'
def get_city_list(url) :
AGE_ACCEPT_BUTTON_XPATH = ".//*[@id='columns']/div/div[2]/section/div/div/div/div/div/div[2]/div[2]/a[2]"
COMBOBOX_XPATH = ".//*[@id='select_city']/li/form/div/button"
COMBOBOX_OPTION_XPATH = ".//*[@id='select_city']/li/form/div/div/ul/li[%s]/a/span[1]"
CHOOSE_BUTTON_XPATH = ".//*[@id='select_city']/li/form/button"
pages = []
try:
browser = get_browser()
wait = WebDriverWait(browser, 100)
browser.get(main_page_url)
time.sleep(2)
button_age_accept = browser.find_element_by_xpath(AGE_ACCEPT_BUTTON_XPATH)
button_age_accept.click()
time.sleep(10)
browser.get(url)
i = 2
while(True) :
try :
button_combobox = browser.find_element_by_xpath(COMBOBOX_XPATH)
button_combobox.click()
time.sleep(5)
element_xpath = COMBOBOX_OPTION_XPATH % i
option_in_combobox = browser.find_element_by_xpath(element_xpath)
# wait.until(EC.invisibility_of_element_located((By.XPATH, element_xpath)))
# option_in_combobox = WebDriverWait(browser, 10).until(lambda browser : browser.find_element_by_xpath(element_xpath))
option_in_combobox.click()
time.sleep(5)
button_choose = browser.find_element_by_xpath(CHOOSE_BUTTON_XPATH)
button_choose.click()
time.sleep(5)
pages.append(browser.current_url)
i += 1
except Exception, e:
print e
break
browser.close()
return pages
except Exception, e:
info = 'Generic exception\n'
print e
return []
get_city_list(basic_url)
我也尝试使用滚动条,尝试将其向下移动,但仍然没有效果。我只能滚动位于此下拉框顶部的页面:
#!/bin/env/python
# -*- coding: utf-8 -*-
import time
from selenium.webdriver.common.by import By
from selenium.webdriver.support.wait import WebDriverWait
from selenium import webdriver
from selenium.webdriver.common.action_chains import ActionChains
from selenium.common.exceptions import NoSuchElementException
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import Select
def get_browser():
return webdriver.Chrome()
main_page_url = "http://example.com/"
basic_url = 'http://example.com/ogloszenia-kobiet.html'
def get_city_list(url) :
AGE_ACCEPT_BUTTON_XPATH = ".//*[@id='columns']/div/div[2]/section/div/div/div/div/div/div[2]/div[2]/a[2]"
COMBOBOX_XPATH = ".//*[@id='select_city']/li/form/div/button"
COMBOBOX_OPTION_XPATH = ".//*[@id='select_city']/li/form/div/div/ul/li[%s]/a/span[1]"
CHOOSE_BUTTON_XPATH = ".//*[@id='select_city']/li/form/button"
pages = []
try:
browser = get_browser()
wait = WebDriverWait(browser, 100)
browser.get(main_page_url)
time.sleep(2)
button_age_accept = browser.find_element_by_xpath(AGE_ACCEPT_BUTTON_XPATH)
button_age_accept.click()
time.sleep(10)
browser.get(url)
i = 2
while(True) :
try :
button_combobox = browser.find_element_by_xpath(COMBOBOX_XPATH)
button_combobox.click()
time.sleep(5)
element_xpath = COMBOBOX_OPTION_XPATH % i
option_in_combobox = browser.find_element_by_xpath(element_xpath)
actionChains = ActionChains(browser)
scrollbar = browser.find_element_by_xpath("/html/body/section/section[2]/div/div[2]/section/div/div/div/div[1]/ul/li/form/div/div/ul")
actionChains.click_and_hold(scrollbar).perform()
actionChains.move_by_offset(0,10+i).perform()
actionChains.release()
browser.execute_script("arguments[0].scrollIntoView();", option_in_combobox)
option_in_combobox.click()
browser.execute_script("window.scrollTo(0, 0);")
button_choose = browser.find_element_by_xpath(CHOOSE_BUTTON_XPATH)
button_choose.click()
time.sleep(5)
pages.append(browser.current_url)
i += 1
except Exception, e:
print e
break
browser.close()
return pages
except Exception, e:
info = 'Generic exception\n'
print e
return []
pages = get_city_list(basic_url)
for p in pages :
with open('links.txt', 'a') as the_file:
the_file.write(p)
the_file.write('\n')
------------------------------------------ -------------------------------------------------- -------------------------------------- 更新: ----------------------------------------------- -------------------------------------------------- ----------------------------------
现在,我使用的是Kubuntu 14.04
。我有Python 2.7.11
和Selenium 2.49.2
。我当前的代码:
#!/bin/env/python
# -*- coding: utf-8 -*-
import time
from selenium.webdriver.common.by import By
from selenium.webdriver.support.wait import WebDriverWait
from selenium import webdriver
from selenium.webdriver.common.action_chains import ActionChains
from selenium.common.exceptions import NoSuchElementException
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import Select
# def get_browser():
# options = webdriver.ChromeOptions()
# options.add_argument("--start-maximized")
# return webdriver.Chrome(chrome_options=options)
def get_browser():
return webdriver.Firefox()
main_page_url = "http://example.com/"
basic_url = 'http://example.com/ogloszenia-kobiet.html'
def get_city_list(url) :
AGE_ACCEPT_BUTTON_XPATH = ".//*[@id='columns']/div/div[2]/section/div/div/div/div/div/div[2]/div[2]/a[2]"
COMBOBOX_XPATH = ".//*[@id='select_city']/li/form/div/button"
COMBOBOX_OPTION_XPATH = ".//*[@id='select_city']/li/form/div/div/ul/li[%s]/a/span[1]"
CHOOSE_BUTTON_XPATH = ".//*[@id='select_city']/li/form/button"
pages = []
try:
browser = get_browser()
wait = WebDriverWait(browser, 100)
browser.get(main_page_url)
time.sleep(2)
button_age_accept = browser.find_element_by_xpath(AGE_ACCEPT_BUTTON_XPATH)
button_age_accept.click()
time.sleep(10)
browser.get(url)
i = 2
while(True) :
try :
button_combobox = browser.find_element_by_xpath(COMBOBOX_XPATH)
button_combobox.click()
time.sleep(5)
element_xpath = COMBOBOX_OPTION_XPATH % i
option_in_combobox = browser.find_element_by_xpath(element_xpath)
option_in_combobox.click()
button_choose = browser.find_element_by_xpath(CHOOSE_BUTTON_XPATH)
button_choose.click()
time.sleep(5)
pages.append(browser.current_url)
i += 1
except Exception, e:
print e
break
browser.close()
return pages
except Exception, e:
info = 'Generic exception\n'
print e
return []
pages = get_city_list(basic_url)
for p in pages :
with open('links.txt', 'a') as the_file:
the_file.write(p)
the_file.write('\n')
对于 Firefox,代码在元素“Gdańsk”处退出并显示一条消息:string indices must be integers
,因此这意味着它没有找到我的组合框中的每个元素。
对于 Chrome 和 Windows XP,它在 'Bielsko-Biała' 处退出,所以这意味着它没有找到我的组合框中的每个元素。 ...
我该如何解决这个问题?
【问题讨论】:
请记住,该网站的用户年仅 13 岁,并且是工作中访问该网站的专业人士,请不要链接到您的问题中包含裸露内容的网站。在问题本身中包含足够的详细信息,以便可以回答问题。 【参考方案1】:移动到元素然后点击:
from selenium.webdriver.common.action_chains import ActionChains
actions = ActionChains(browser)
actions.move_to_element(option_in_combobox).click().perform()
或者,scroll into it's view:
browser.execute_script("arguments[0].scrollIntoView();", option_in_combobox)
或者,点击元素via javascript:
browser.execute_script("arguments[0].click();", option_in_combobox)
对于 Firefox,代码在元素 'Gdańsk' 处退出并显示一条消息:字符串索引必须是整数,因此这意味着它不会在我的组合框中找到每个元素。
selenium 2.49 中存在可能导致此TypeError
的问题。您需要降级到 2.48:
pip install selenium==2.48
Python & Selenium Click and "TypeError: string indices must be integers"
【讨论】:
首先:感谢您的回答。第二:我按照您的建议修改了我的代码,并且 1)您的第二种方法(此代码:gist.github.com/anonymous/00789e9cc3c13fc6477c)给了我Element is not clickable at point ...
,但没有找到我需要的所有链接,只是其中一些 2)您的第一种方法(我的代码:gist.github.com/anonymous/880841d0166943133a42) 给出了element not visible
并且根本找不到任何链接 3) 你的第三种方法(我的代码:gist.github.com/anonymous/6261a924b4f15760742f)也给出了element not visible
并且任何链接都被保存了......有什么想法吗?
@Katie 请先尝试 Cyril 的回答,看看是否有帮助。让我们看看问题是否仍然存在。谢谢。
@Katie 请查看更新。它应该解释你的字符串索引必须是整数错误。【参考方案2】:
如前所述,您应该先移动到选项元素,然后再单击它:actions.move_to_element(option_in_combobox).click().perform()
。现在“button_choose”元素不可见,因为浏览器向下滚动。要解决此问题,您需要滚动到顶部,然后单击按钮:
browser.execute_script("window.scrollTo(0, 0);") # scroll to top
button_choose = browser.find_element_by_xpath(CHOOSE_BUTTON_XPATH)
button_choose.click()
【讨论】:
这也行不通。我的代码:codepad.org/Utw8X1Dw 仅获取一些可用链接,而不是全部。滚动到此下拉框底部的城市似乎仍然存在问题。 您的代码对我有用。我将 i 设置为 40,它适用于所有位于底部的城市(包括“zielona-gora”)。注意:我必须最大化 Chrome 才能让它工作,Firefox 开箱即用。 这其实很奇怪。在 Kubuntu 和 Windows 上尝试了我的代码,并且有相同的错误,我发布的代码的示例错误(在 Windows 上测试):gist.github.com/anonymous/8a6d50228ac12cc4cc72,gist.github.com/anonymous/eac439ef03ce9509e776,修改后的代码:gist.github.com/anonymous/a0fc50801436948bbf5c 这确实很奇怪。我刚刚运行了要点,它按预期工作(Selenium 2.49.2 / Python 2.7 / Ubuntu 14.04) 我在我的 Kubuntu 14.04 上测试了它。我有 Python 2.7.11 和 Selenium 2.49.2(我同时从 2.48 更新)。但是现在,代码给了我这样的信息string indices must be integers
【参考方案3】:
我在 java 中尝试过,它的工作非常好。我请求请查看 for 循环,主要是因为在这里我可以一一选择选项。我刚刚使用了 Thread.sleep,因为我知道我们也可以使用等待。为了使类似于我刚刚附加到 StringBuffer 的问题,我知道我们可以添加到 java 中的任何收集器。我没有完全接受年龄等,因为我说我专注于那个下拉选择..
public class Dog
private WebDriver driver;
private String baseUrl;
private StringBuffer verificationErrors = new StringBuffer();
@BeforeClass()
public void setUp() throws Exception
// driver = new FirefoxDriver();
System.setProperty("webdriver.chrome.driver", "E:\\selenium_setups\\chromedriver_win32\\chromedriver.exe");
driver=new ChromeDriver();
driver.manage().window().maximize();
baseUrl = "http://example.com/";
driver.manage().timeouts().implicitlyWait(30, TimeUnit.SECONDS);
@Test
public void test***Issue() throws Exception
driver.get(baseUrl);
driver.findElement(By.cssSelector(".btn.btn-success")).click();
driver.get("http://example.com/ogloszenia-kobiet.html");
List<WebElement> options=driver.findElements(By.xpath(".//*[@id='select_city']/li/form/div/div/ul/li"));
for(int i=1; i<=options.size(); i++)
driver.findElement(By.xpath("(//button[@type='button'])[4]")).click();
driver.findElement(By.xpath("//ul[@id='select_city']/li/form/div/div/ul/li["+i+"]")).click();
driver.findElement(By.cssSelector("button.btn.btn-success")).click();
Thread.sleep(5000);
verificationErrors.append(driver.getCurrentUrl());
System.out.println(driver.getCurrentUrl() +" >>> iteration " +i);
driver.navigate().to("http://example.com/ogloszenia-kobiet.html");
Thread.sleep(5000);
我希望这将帮助您在 python 中选择下拉值..
输出
谢谢你, 壁画
【讨论】:
谢谢。根据@alecxe 的建议,我降级为Selenium 2.48
,并修改了您的代码(实际上已将其翻译为Python),但问题仍然存在。我的代码仅获取下拉框的可见部分,但是,当我在 Firefox 中最大化浏览器窗口时,它为我提供了比以前的方法更多的链接(直到“克拉科夫”)。但是,在到达“克拉科夫”之后,程序结束,并且无法从下拉框的底部获取元素。我修改后的代码在这里:gist.github.com/anonymous/9cb82acf839d6b92731d
由于我需要使用此代码构建 Windows 可执行文件,因此我也在 Windows XP 和 Chrome 上进行了尝试。在那里,问题和以前一样。您的代码只能到达“Bielsko-Biala”并结束,说Element is not clickable at point (1018, 508)
... Huh
@Katie,更改了 chromedriver。它工作得很好看输出图像。我使用这个 xpath //ul[@id='select_city']/li/form/div/div/ul/li["+i+"] 在下拉列表中选择值。我不习惯跨度。我希望你注意到这一点。谢谢
selenium-server-standalone-2.48.2.jar,WIN 7
我有最新的chromedriver……反正这段代码不行,至少在我的电脑上,还有我朋友的电脑上……【参考方案4】:
在选择“当前不可见的元素”之前尝试这个,然后点击下拉菜单:
browser.execute_script("document.getElementsByClassName('dropdown-menu inner selectpicker')[0].setAttribute('style', '');")
【讨论】:
以上是关于元素当前不可见,因此可能无法与之交互,Selenium Dropdown Box Python的主要内容,如果未能解决你的问题,请参考以下文章
如何避免“元素当前不可见,因此可能无法与” Selenium Webdriver
如何强制Selenium WebDriver点击当前不可见的元素?
如何解决 ElementNotInteractableException:元素在 Selenium webdriver 中不可见?