Eliran Shani is an Automation Engineer at BlazeMeter and holds an MBA and B.Sc in Software Engineering. Since 2009, Eliran has held multiple technological roles, including software testing, technical support, and automation engineering. In 2012, Eliran started his own venture: 'EATV' - a food ordering application directly on the SAMSUNG Smart TV. He also worked in Kaltura for three years, where he had experience with Fortune 500 Companies. Eliran is an eternal optimist and passionate about UX and creating high quality products.

Learn JMeter in 5 Hours

Start Learning
Slack

Test Your Website Performance NOW!

arrow Please enter a valid URL
May 08 2017

How to Understand Your Selenium WebDriver Code and Run it with Taurus

Selenium is a popular open-source functional testing framework, widely used for testing web-based applications. With Selenium you can control web drivers to emulate user actions.


But Selenium is not a single purpose tool. Each of its four components answers a different organization testing need:

 

  • Selenium Integrated Development Environment (IDE) - a Firefox Add-On that records, edits and debugs tests.
  • Selenium Remote Control (RC) - a server that automatically launches and terminates browsers, and acts as a HTTP proxy for web requests from them
  • Selenium Webdriver - a tool for automating web application testing, which provides a friendly API that's easy to explore and understand. This is the part we will be focusing on.
  • Selenium Grid - a tool that supports distributed test execution. Selenium Grid runs your tests in a distributed test execution environment

 

If you’re new to functional testing and Selenium, we recommend you start with Selenium IDE. If you are more advanced in Selenium, Taurus, an open-source automated testing framework, supports Selenium scripts written in the Python + Unit Testing convention. Taurus also supports Java + JUnit, Java + TestNG, Ruby + RSpec and JavaScript + Mocha. It will soon support the Pytest convention as well.

 

If you’re getting to know Selenium, this blog post is for you. This blog post will explain a basic Selenium code written in Python under the Unit Test convention. This code instructs Selenium to open a certain website (blazedemo.com in our case) and find and purchase a flight ticket. Each part of the code is explained in the code’s comments, after the pound sign (#) and a further explanation is provided as well. Afterwards, we will show you how to run and automate it in Taurus.

 

Let’s get started. We will start with the full code, and then break it down.

 

Explaining a Selenium Python Code

 

This is the full code:

 

# Must: import unittest library
import unittest

# Must: import 'webdriver' library
from selenium import webdriver

# Optional: import 'By' for ease of use
from selenium.webdriver.common.by import By

# Optional: import 'sleep' for browser's time issues
from time import sleep

# Global 'url' variable to set the relevant website where we run our tests
url = "http://blazedemo.com"

"""Create a class 'purchaseTicketTest' that includes:

1. setUp - ChromeDriver initiation
2. functions - that can be used throughout the project
3. test steps - that run one after another
4. tearDown - Closing ChromeDriver

"""

class purchaseTicketTest(unittest.TestCase):

   def setUp(self):

       """ Create ChromeDriver instance with blank page, wait policy of 10 seconds and maximize the window"""

       # Initiate ChromeDriver instance
       self.driver = webdriver.Chrome()

       # Open 'blazedemo.com' home page
       self.driver.get("http://blazedemo.com")

       # Set default timeout for locating and element in the DOM (10 seconds)
       self.driver.implicitly_wait(10)

       # Maximize window
       self.driver.maximize_window()



   def save_screenshot(self):
       """ Save screenshot """
       name = "Blazedemo_screenshot"
       self.driver.get_screenshot_as_file(name + ".png")

   def verify_url(self, actual_url, expected_url):
       """ Compare 2 arguments """
       unittest.TestCase.assertEquals(self, actual_url, expected_url,
                                      "Actual url: " + actual_url + " is not equal to expected url: " + expected_url)

   def find_flight_ticket(self):
       """ Find flight tickets """

       # Choose departure city
       self.driver.find_element(By.XPATH, "//select[@name='fromPort']/option[text()='Mexico City']").click()

       # Choose destination city
       self.driver.find_element(By.XPATH, "//select[@name='toPort']/option[text()='New York']").click()

       # Find Flights
       self.driver.find_element(By.CLASS_NAME, 'btn-primary').click()

       # For debugging purpose
       sleep(3)

       actual_url = self.driver.current_url
       # Verify the actual URL is equal to the expected URL
       self.verify_url(actual_url=actual_url, expected_url="http://blazedemo.com/reserve.php")

   def choose_flights(self):
       """ Choose the relevant flight """

       self.driver.find_element(By.CLASS_NAME, "btn-small").click()

       # For debugging purpose
       sleep(3)

       actual_url = self.driver.current_url
       # Verify the actual URL is equal to the expected URL
       self.verify_url(actual_url=actual_url, expected_url="http://blazedemo.com/purchase.php")

   def purchase_flight(self):
       """ Purchase flight and fill out form"""
       self.driver.find_element(By.ID, 'inputName').send_keys("Michael Jordan")
       self.driver.find_element(By.ID, 'address').send_keys("75th Avenue")
       self.driver.find_element(By.ID, 'city').send_keys("Chicago")
       self.driver.find_element(By.ID, 'state').send_keys("Illinois")
       self.driver.find_element(By.ID, 'zipCode').send_keys("12345")
       self.driver.find_element(By.ID, 'creditCardNumber').send_keys("4580123412341234")
       self.driver.find_element(By.ID, 'nameOnCard').send_keys("Air Mike")

       # Click purchase flight
       self.driver.find_element(By.CLASS_NAME, 'btn-primary').click()

       # For debugging purpose
       sleep(3)

       actual_url = self.driver.current_url
       # Verify the actual URL is equal to the expected URL
       self.verify_url(actual_url=actual_url, expected_url="http://blazedemo.com/confirmation.php")

   def capture_flight_ticket_confirmation(self):
       """ Capture flight ticket order screenshot """
       sleep(3)
       self.save_screenshot()

   def test_method(self):
      
       # Test step #1
       self.find_flight_ticket()

       # Test step #2
       self.choose_flights()

       # Test step #3
       self.purchase_flight()

       # Test step #4
       self.capture_flight_ticket_confirmation()

   def tearDown(cls):
       """ Close ChromeDriver """
       cls.driver.quit()

 

This is the same code with explanations:

 

The following lines will import several external libraries that our code will inherit and use.

 

  • unittest (*Must) - this means our code will be interpreted under the unittest testing convention. Additional information on unittest with Python can be found here.
  • selenium.webdriver (*Must) - our code will use common browser methods from Webdriver, such as click, finding elements, insert text etc. Additional info on Webdriver with Python can be found here.
  • selenium.webdriver.common.by (*Optional but very recommended) - A very handy class that is useful when finding element By. a certain html tag, attribute, id, name etc.
  • time.sleep (*Optional) - desperate times call for desperate measures. We should rarely use sleep to pause our code for an action to occur in the browser (such as alert, elements animation, process request etc..). Instead, we should use wait.until as mentioned here.

 

# Must: import unittest library
import unittest
# Must: import 'webdriver' library
from selenium import webdriver
# Optional: import 'By' for ease of use
from selenium.webdriver.common.by import By
# Optional: import 'sleep' for browser's time issues
from time import sleep

 

This is how we start our unittest convention:
 

"""Create a class 'purchaseTicketTest' that includes:
1. setUp - ChromeDriver initiation
2. functions - that can be used throughout the project
3. test steps - that run one after another
4. tearDown - Closing ChromeDriver
"""
class purchaseTicketTest(unittest.TestCase):

 

The setUp runs once at the initiation of the class and is responsible for setting up a browser (Chrome in our case) with attributes.

 

   def setUp(self):
       """ Create ChromeDriver instance with blank page, wait policy of 10 seconds and maximize the window"""

       # Initiate ChromeDriver instance
       self.driver = webdriver.Chrome()
       # Open blank page
       self.driver.get("http://blazedemo.com")
       # Set default timeout for locating and element in the DOM (10 seconds)
       self.driver.implicitly_wait(10.0)
       # Maximize window
       self.driver.maximize_window()

 

The functions below are used throughout the code. They are not actual steps, only functions.

 

  • save_screenshot - saves the screenshot and stores the file in the same test directory.
  • Verify_url - this function compares two strings and executes unittest.TestCase.assertEquals.
  • find_flights (test #1) - searches flights from and to locations in the dropdown menu and clicks the “find” button. It also verifies the redirected url as well, of course.
  • choose_flight (test #2) - choose a flight and verify the redirected url.
  • purchase_flight (test #3) - fill out information in the text fields
  • capture_fight_ticket_confirmation (test #4) - save the screenshot function

 

   def save_screenshot(self):
       """ Save screenshot """
       name = "Blazedemo_screenshot"
       self.driver.get_screenshot_as_file(name + ".png")

   def verify_url(self, actual_url, expected_url):
       """ Compare 2 arguments """
       unittest.TestCase.assertEquals(self, actual_url, expected_url,
                                      "Actual url: " + actual_url + " is not equal to expected url: " + expected_url)


def find_flight_ticket(self):
   """ Find flight tickets """

   # Choose departure city
   self.driver.find_element(By.XPATH, "//select[@name='fromPort']/option[text()='Mexico City']").click()

   # Choose destination city
   self.driver.find_element(By.XPATH, "//select[@name='toPort']/option[text()='New York']").click()

   # Find Flights
   self.driver.find_element(By.CLASS_NAME, 'btn-primary').click()

   # For debugging purpose
   sleep(3)

   actual_url = self.driver.current_url
   # Verify the actual URL is equal to the expected URL
   self.verify_url(actual_url=actual_url, expected_url="http://blazedemo.com/reserve.php")

def choose_flights(self):
   """ Choose the relevant flight """

   self.driver.find_element(By.CLASS_NAME, "btn-small").click()

   # For debugging purpose
   sleep(3)

   actual_url = self.driver.current_url
   # Verify the actual URL is equal to the expected URL
   self.verify_url(actual_url=actual_url, expected_url="http://blazedemo.com/purchase.php")

def purchase_flight(self):
   """ Purchase flight and fill out form"""
   self.driver.find_element(By.ID, 'inputName').send_keys("Michael Jordan")
   self.driver.find_element(By.ID, 'address').send_keys("75th Avenue")
   self.driver.find_element(By.ID, 'city').send_keys("Chicago")
   self.driver.find_element(By.ID, 'state').send_keys("Illinois")
   self.driver.find_element(By.ID, 'zipCode').send_keys("12345")
   self.driver.find_element(By.ID, 'creditCardNumber').send_keys("4580123412341234")
   self.driver.find_element(By.ID, 'nameOnCard').send_keys("Air Mike")

   # Click purchase flight
   self.driver.find_element(By.CLASS_NAME, 'btn-primary').click()

   # For debugging purpose
   sleep(3)

   actual_url = self.driver.current_url
   # Verify the actual URL is equal to the expected URL
   self.verify_url(actual_url=actual_url, expected_url="http://blazedemo.com/confirmation.php")

def capture_flight_ticket_confirmation(self):
   """ Capture flight ticket order screenshot """
   sleep(3)
   self.save_screenshot()

 

Running all tests steps one after another as follows:

 

def test_method(self):
   # Test step #1
   self.find_flight_ticket()
   # Test step #2
   self.choose_flights()
   # Test step #3
   self.purchase_flight()
   # Test step #4
   self.capture_flight_ticket_confirmation()

 

The crucial tearDown function closes the webdriver browser session when all the tests are done:
 

   def tearDown(self):
       """ Close ChromeDriver """
       self.driver.quit()

 

Running Your Selenium Python File in Taurus

To run this test in Taurus you must follow these steps:

 

1. Install the Taurus Python repository.

 

sudo pip install bzt

 

2. Install ChromeDriver.

 

3. Save your unittest python file (as described above)

 

4. Save your .yaml file with the convention mentioned here.

 

An example .yaml file that runs a concurrency of 20:

 

---
Execution:
- executor: selenium
  concurrency: 20
  Scenario:
	  script: <FILE_NAME>.yml

 

*Note that the YAML and PY files need to be in the same folder.

 

5. The folder structure should includes two files:

 

  • selenium.yml
  • test_python_taurus.py

 

Running Your Selenium Python File in Taurus


6. Run the test with the following command:

 

bzt selenium.yml

 

7. Wait for the Taurus engine to initiate. The Console should look like this:

 

taurus console after running selenium python

 

8. At this point, the ChromeDriver should step up and the test should start.

 

9. Once the flow is done, the terminal should return the following:

 

terminal after running selenium python

 

10. The folder should create the following files as well:

 

  • A screenshot generated by the script in the same folder
  • An artifacts folder which includes relevant logs for debug purpose

 

Running Your Selenium Python File in Taurus

 

The following video shows a full flow when running a Selenium Python test locally under Taurus engine:

 

 

A link to Taurus demo repository can be found here.

 

That’s it! To learn more about running your scripts through Taurus, check out this free webinar: “Using Taurus to Automate JMeter and Selenium Tests”.

 

To learn more about load testing with BlazeMeter, which supports Selenium Webdriver tests with JMeter, just put your URL or JMX file in the box below, and your test will start in minutes.

 

     
arrow Please enter a valid URL

Interested in writing for our Blog?Send us a pitch!

We're working on starting your first test

Testing 20 Virtual Users

Starting your test in around 2-4 minutes. Your report will appear once we've gathered the data.

0

Status: Preparing Your Test

Your email is required to complete the test. If you proceed, your test will be aborted.