Home > Software engineering >  Using Selenium within python functions
Using Selenium within python functions

Time:01-27

While my python selenium code works well, I identified several sections of it in which I am waiting to click on an XPATH located item and therefore tried to define a function to do so as follows:

def click_xpath(browser, xpath_string: str):
    """ locates a button by XPATH
        and clicks on it
    """
    WebDriverWait(browser, 10).until(
        EC.element_to_be_clickable((By.XPATH, xpath_string))
    ).click()
    return browser

and call it as follows:

driver = click_xpath(driver, "/html/body/div[5]/div[3]/div/button")

but then the next instruction:

find_textbox = driver.find_element_by_id("search")

fails with the following:

selenium.common.exceptions.ElementNotInteractableException: Message: element not interactable

The previous working code that I attempted substituting by calling my function was:

WebDriverWait(driver, 10).until(
   EC.element_to_be_clickable((By.XPATH, "/html/body/div[5]/div[3]/div/button"))
).click()

which worked well, with subsequent uses of driver proceeding normally.

What am I overlooking? Thanks

PS Assuming this can be done, what type hind should I use for the return object of my function?

CodePudding user response:

I guess the problem here is as following:
When you clicking the element after waiting for the element to be clickable with click_xpath it works correctly but when you trying to click it immediately with

find_textbox = driver.find_element_by_id("search")

You are getting the error since you are trying to click the element too early.
So, you are simply missing a delay there.
Try changing from

find_textbox = driver.find_element_by_id("search")

To

find_textbox =  WebDriverWait(browser, 10).until(EC.element_to_be_clickable((By.ID, search)))

I think this will resolve your problem

CodePudding user response:

I think

.click 

should be

.click()

also, there is no need to return a driver/browser from this method click_xpath

cause it says just click on the XPath node, right?

also, a ) is missing here

driver = click_xpath(driver, "/html/body/div[5]/div[3]/div/button"

I would use something like this:

def click_xpath(browser, xpath_string):
    WebDriverWait(browser, 10).until(EC.element_to_be_clickable((By.XPATH, xpath_string))).click()
    print('Clicked on the', xpath_string, ' node')

somenode = click_xpath(driver, "/html/body/div[5]/div[3]/div/button")

and the second question that you asked, what

what type hind should I use for the return object of my function?

.click() method returns void, so if you are using it on a web element then there is no need to return anything. However, you could do the below in case you are very knee on returning.

Also, note that, WebDriverWait(browser, 10).until(EC.element_to_be_clickable((By.XPATH, xpath_string))) will return a web element if found.

Code:

def click_xpath(browser, xpath_string):
    web_element = WebDriverWait(browser, 10).until(EC.element_to_be_clickable((By.XPATH, xpath_string)))
    print('Clicked on the', xpath_string, ' node')
    return web_element

somenode = click_xpath(driver, "/html/body/div[5]/div[3]/div/button")
somenode.click()
  •  Tags:  
  • Related