Non blocking wait in selenium in Python

This article teaches how we can prevent blocking call when automating the web browser with selenium. This article is about non blocking wait in selenium with Python programming.

While automating the web browser, we need to wait for the javascript elements to appear before performing some action on them. To do this, we generally use sleep( ) method to wait for the elements to appear. This is a blocking call. By saying this, we mean that it makes the program to sleep for some seconds and doesn’t care if the elements appeared or not. This slows down the program and so is not a good idea to wait for some seconds. The solution for this could be to wait until those elements appear and then wait no more.

Let’s see how we can do this.

Importing Libraries

Import the following Python libraries:

from selenium import webdriver 
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
from selenium.common.exceptions import TimeoutException

Let say we want to search something on google and we need to automate this thing. Follow these steps to add the query in the google search bar as soon as the search bar loads press the search button.

Step 1

In the first step, we would configure the chrome web driver. See the following code.

options = webdriver.ChromeOptions()
options.add_argument('--ignore-certificate-errors')
options.add_argument('--incognito')
driver = webdriver.Chrome(path_to_the_chrome_webdriver,
                          chrome_options=options)

Add the path of the chrome driver file that you downloaded at the place where path_to_the_chrome_webdriver is written.

Step 2

Store the URL, search query, X_path of the javascript elements into separate variables. See the following code and try to understand the code by reading the comments.

# store the url of the google webpage
# in the url variable
url = 'https://www.google.com/'

# store the query in a variable
search_query = 'codespeedy.com'

# store the x_path of the google search box
search_box_Xpath = '/html/body/div/div[3]/form/div[2]/div[1]/div[1]/div/div[2]/input'

# store the x_path of the google search button
search_button_Xpath = '/html/body/div/div[3]/form/div[2]/div[1]/div[3]/center/input[1]'

# this
driver.get(url)

Note: X path can be copied by inspecting the corresponding element in the web browser and then
right-click -> copy -> copy x-path.

Step 3

Make a function is_element_appeared which is the main function we are talking in this article. This function will tell the program that the corresponding element has appeared.

See the following code.

def is_element_appeared(element_Xpath, timeout = 30): 
    try: 
        WebDriverWait(driver, timeout).until(EC.visibility_of_element_located((By.XPATH, element_Xpath))) 
        return True
    except TimeoutException:
        raise RuntimeError("Something went wrong!!")
        return False

Function description:

  1. element_Xpath: This is the x path of the javascript element.
  2. timeout: This is the maximum time to wait for the element to get appear. If not appear, raise the timeout error.
  3.  driver: It is the object of the web driver initialized earlier.
  4. The code waits until the corresponding element appears by locating the XPath of the element.
  5.  The function returns true if the element appeared before timeout else raises an error.

Step 4

In the last step, we call the above function for each javascript element that we want to wait for.

See the code below.

# waiting for the search box till it appears
if (is_element_appeared(search_box_Xpath)):  
    search_box = driver.find_element_by_xpath(search_box_Xpath) 
    search_box.send_keys(search_query)

# waiting for the search button till it appears
if (is_element_appeared(search_button_Xpath)): 
    search_button = driver.find_element_by_xpath(search_button_Xpath)
    search_button.click()

If the function returns true we perform the action on the visible element. Here as soon as the search box appears, we add our query in the search box. After that wait for the search button and click it after it appears to search that google query.

Full code

Now it’s time to see the complete code. Below is the complete Python code for Non blocking wait in selenium:

from selenium import webdriver 
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
from selenium.common.exceptions import TimeoutException
options = webdriver.ChromeOptions()
options.add_argument('--ignore-certificate-errors')
options.add_argument('--incognito')
driver = webdriver.Chrome(path_to_the_chrome_webdriver,
                          chrome_options=options)

# store the url of the google webpage
# in the url variable
url = 'https://www.google.com/'

# store the query in a variable
search_query = 'codespeedy.com'

# store the x_path of the google search box
search_box_Xpath = '/html/body/div/div[3]/form/div[2]/div[1]/div[1]/div/div[2]/input'

# store the x_path of the google search button
search_button_Xpath = '/html/body/div/div[3]/form/div[2]/div[1]/div[3]/center/input[1]'

# Note: X path can be copied by inspecting
# the corresponding element in the web browser
# and then right click -> copy -> copy x-path

# this
driver.get(url) 

def is_element_appeared(element_Xpath, timeout = 30): 
    try: 
        WebDriverWait(driver, timeout).until(EC.visibility_of_element_located((By.XPATH, element_Xpath))) 
        return True
    except TimeoutException:
        raise RuntimeError("Something went wrong!!")
        return False

# waiting for the search box till it appears
if (is_element_appeared(search_box_Xpath)):  
    search_box = driver.find_element_by_xpath(search_box_Xpath) 
    search_box.send_keys(search_query)

# waiting for the search button till it appears
if (is_element_appeared(search_button_Xpath)): 
    search_button = driver.find_element_by_xpath(search_button_Xpath)
    search_button.click()

I hope you liked the article.

 

Leave a Reply