如何使用 Selenium 和 Python 单击输入元素

How to click on an input element using Selenium and Python

我正在尝试在 Selenium documentation 网站中单击文本为 Python 的选项卡。

HTML:

<input type="radio" name="tabsetcode2" id="tab1code2" aria-controls="pythoncode2">

但我正面临 TimeoutException:

selenium.common.exceptions.TimeoutException: Message:

代码试验:

driver.get('https://www.selenium.dev/documentation/en/')
WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.CSS_SELECTOR, "input[aria-controls='pythoncode2']"))).click()

谁能帮我点击 Python 选项卡?

尝试通过 xpath 等待

WebDriverWait(browser, 20).until(EC.element_to_be_clickable((By.XPATH, '*//div[@class="tabset"]/label[2]'))).click()

如果还是不行,等到可见再试试

WebDriverWait(browser, 20).until(EC.presence_of_element_located((By.XPATH, '*//div[@class="tabset"]/label[2]'))).click()

首先,优先使用 Id > Css select 或 > XPaths。所以示例代码可能是 (By.CSS_SELECTOR, "#pythoncode2") 或更好的 (By.ID, "pythoncode2").

然而,无论如何,这不是一个可点击的元素,所以尽管等待 20 秒,它总是会超时等待它变为 'clickable'。 (单选按钮的圆圈具有 left -1704px 的样式,如果您通过 F12 和 select 该选项卡在浏览器上进入“开发人员模式”,则该样式不在屏幕上。驱动程序会考虑其视口之外的任何内容无法点击)

可点击元素为目标标签;没有id,但是可以通过CSS找到:(By.CSS_SELECTOR, "label[for=tab1code2]")

这是我的工作代码来证明它有效:

from selenium import webdriver

if __name__ == '__main__':
    driver = webdriver.Chrome("./chromedriver")
    driver.get('https://www.selenium.dev/documentation/en/')
    driver.find_element_by_css_selector("label[for=tab1code2]").click()

您可以点击标签,它会起作用。

driver.get('https://www.selenium.dev/documentation/en/')
WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.XPATH, "//label[@for='tab1code2']"))).click()

该元素确实可以点击。但是它是用label标签绑定的。

有关绑定标签和信息的更多信息here

使用 EC.element_to_be_clickable 还可以确保元素可见,但事实并非如此。

class element_to_be_clickable(object):
    """ An Expectation for checking an element is visible and enabled such that
    you can click it."""

您可以通过调用is_enabled确认它是可点击的。此方法仅验证属性 disabled 是否为假。

driver.find_element_by_css_selector("input[aria-controls='pythoncode2']").is_enabled()

driver.find_element_by_css_selector("input[aria-controls='pythoncode2']").get_attribute('disabled') != "true"

结果:

True

但是 EC.element_to_be_clickable 也会调用 is_displayed 来确定该元素是否也可见

driver.find_element_by_css_selector("input[aria-controls='pythoncode2']").is_displayed()

结果:

False

这就是为什么,无论你等多久,它永远不会成真。

要单击 input 元素,您可以将目标改为 label 元素。它们与属性 for=id

绑定在一起

你的情况

driver.find_element_by_css_selector('[for="tab1code2"]')

还有:

driver.find_element_by_css_selector('[for="tab1code2"]').is_enabled()
driver.find_element_by_css_selector('[for="tab1code2"]').is_displayed()

两个 returns: True

如果您尝试使用您选择的 css 选择器单击该元素,则会引发以下异常:

ElementNotInteractableException: Message: element not interactable"

原因是 type="radio" 属性。

相反,您应该尝试使用以下 css 选择器单击下面的标签元素:

("label[for=tab1code2]")

因此,您的代码应如下所示:

WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.CSS_SELECTOR, "label[for=tab1code2]"))).click()