How to do xpath "and" / condition query correctly?
Question:
I am trying to set a checkmark on the prime option on amazon.fr.
Here is the link (the prime option is on the left): https://www.amazon.fr/gp/browse.html?node=2036893031.
Here is an image that shows the field I want to checkmark: https://ibb.co/ZY3mK3Z
I have it almost working. But it does not work for all amazon-categories, that’s why I added the "and"-operator. Here is my xpath-query:
driver = webdriver.Chrome()
driver.get(category_url)
driver.find_element_by_xpath('//*[@id="leftNav"]/h4[text()="%s"]/following-sibling::ul//input[contains(@name, "s-ref-checkbox-")] and //*[@id="leftNav"]/h4[text()="%s"]/following-sibling::ul//input[contains(@name, "s-ref-checkbox-")]//i[contains(@class, "icon-prime")]' % ("Option d'expédition", "Option d'expédition"))
driver.click()
How can I format my query correctly? Is the and operator even necessary? I get the following error message:
TypeError: Failed to execute ‘evaluate’ on ‘Document’: The result is
not a node set, and therefore cannot be converted to the desired type.
Answers:
I think you are trying to click without passing the WebElement.
You can find the checkbox based on the position of Prime label next to it.
Try the following xpath,
myprime = driver.find_element_by_xpath("//*[contains(@class,'icon-prime a-icon-small s-ref-text-link')]/parent::span/parent::label/input")
myprime.click();
I just tried the XPath below and it uniquely located the element
//label[.//i[contains(@class, 'a-icon-prime')]]/input
^ find a LABEL tag
^ that has a child I tag
^ that contains the class 'a-icon-prime' (indicating the prime logo)
^ then find an INPUT under the LABEL
The minimal working XPath locator would be:
//i[contains(@class,'small') and contains(@class,'prime')]
For better robustness and reliability I would recommend wrapping it into an Explicit Wait like:
prime = WebDriverWait(driver, 10).until(
expected_conditions.presence_of_element_located((By.XPATH, "//i[contains(@class,'small') and contains(@class,'prime')]")))
prime.click()
More information: How to use Selenium to test web applications using AJAX technology
I am trying to set a checkmark on the prime option on amazon.fr.
Here is the link (the prime option is on the left): https://www.amazon.fr/gp/browse.html?node=2036893031.
Here is an image that shows the field I want to checkmark: https://ibb.co/ZY3mK3Z
I have it almost working. But it does not work for all amazon-categories, that’s why I added the "and"-operator. Here is my xpath-query:
driver = webdriver.Chrome()
driver.get(category_url)
driver.find_element_by_xpath('//*[@id="leftNav"]/h4[text()="%s"]/following-sibling::ul//input[contains(@name, "s-ref-checkbox-")] and //*[@id="leftNav"]/h4[text()="%s"]/following-sibling::ul//input[contains(@name, "s-ref-checkbox-")]//i[contains(@class, "icon-prime")]' % ("Option d'expédition", "Option d'expédition"))
driver.click()
How can I format my query correctly? Is the and operator even necessary? I get the following error message:
TypeError: Failed to execute ‘evaluate’ on ‘Document’: The result is
not a node set, and therefore cannot be converted to the desired type.
I think you are trying to click without passing the WebElement.
You can find the checkbox based on the position of Prime label next to it.
Try the following xpath,
myprime = driver.find_element_by_xpath("//*[contains(@class,'icon-prime a-icon-small s-ref-text-link')]/parent::span/parent::label/input")
myprime.click();
I just tried the XPath below and it uniquely located the element
//label[.//i[contains(@class, 'a-icon-prime')]]/input
^ find a LABEL tag
^ that has a child I tag
^ that contains the class 'a-icon-prime' (indicating the prime logo)
^ then find an INPUT under the LABEL
The minimal working XPath locator would be:
//i[contains(@class,'small') and contains(@class,'prime')]
For better robustness and reliability I would recommend wrapping it into an Explicit Wait like:
prime = WebDriverWait(driver, 10).until(
expected_conditions.presence_of_element_located((By.XPATH, "//i[contains(@class,'small') and contains(@class,'prime')]")))
prime.click()
More information: How to use Selenium to test web applications using AJAX technology