Skip to main content

Modularisation and Parameterisation

Reusability and maintenance are key requirements of a successful test automation solution, therefore being able to quickly build frameworks and adapting the frameworks to change is essential.

Within Eggplant, this is a fundamental best practice to ensure concise and sustainable scripts are created whilst also ensuring a simple approach to automation in Eggplant is followed.

The rules to follow when building out modular functionality can be broken down in to 3 rules of thumb:
  1. Identify Reoccurring Scenarios
  2. Reusing Functions Within Functions
  3. Simplifying Approaches
To achieve this, the following methodology should be applied:

    DO: ✅
  • Add parameters to the function to make the function more reusable
  • Limit handlers to specific functionality
  • Break it down for specific groups of behaviours (e.g. handler for launch browser, handler for login, handler for navigating through the main menu)
    Don't ❌
  • Don't over-engineer the solution - We don't need parameters for everything!
  • Don't include actions for a whole flow into one handler (e.g. handler for 'start test' that incorporates all of the separate actions)

Identifying Reoccurring Scenarios

Using the example of our code from earlier best practices (shown below), we can determine that there is 3 key functionality that is repeating through the use case.

  • Launching The Browser
  • Dropdown and Navigate
  • Navigating on Page
Original Test Script:
Repeating / Key Behaviour:

click image:"chrome" // Icon
waitfor 20, image:"refresh" // Icon

set the searchRectangle to (0,70,1920,1039) // Optimises OCR
typetext "https://demo.nopcommerce.com/",returnkey
waitfor 20, image:"nopCommerce" // Logo

moveto text:"Computers"
wait 1 // Optimises OCR
click text:"Desktops"
wait 1.5 // Optimises OCR
waitfor 20, text:"Categories"

click text:"Digital Storm VANQUISH 3"
wait 1.5 // Optimises OCR
waitfor 20, text:"Digital Storm Vanquish 3 Desktop PC"

click text:"ADD TO CART"
wait 2 // Optimises OCR
waitfor 20,text:"The product has been added to your shopping cart"
Launch Browser:
click image:"chrome" // Icon
waitfor 20, image:"refresh" // Icon
set the searchRectangle to (0,70,1920,1039) // Optimises OCR
typetext "https://demo.nopcommerce.com/",returnkey
waitfor 20, image:"nopCommerce" // Logo
Drop Down:
moveto text:"Computers"
wait 1 // Optimises OCR
click text:"Desktops"
wait 1.5 // Optimises OCR
waitfor 20, text:<mark>"Categories"</mark>
Navigation:
click text:"Digital Storm VANQUISH 3"
wait 1.5 // Optimises OCR
waitfor 20, text:"Digital Storm Vanquish 3 Desktop PC"
click text:"ADD TO CART"
wait 2 // Optimises OCR
waitfor 20,text:"The product has been added to your shopping cart"

Using the breakdown of the script above, building out a navigation function and referencing it would look like the following:

Navigate Function:Calling the Function:
to navigate action, validation
click text:action
wait 1.5 // page transition pause
waitfor 20, text:validation
end navigate
navigate ("Digital Storm VANQUISH 3"),("Digital Storm Vanquish 3 Desktop PC")

navigate ("ADD TO CART"),("The product has been added to your shopping cart")

If any changes need to be made to the Navigate flow, a user will need to make only one change, rather than trying to update the occurrences of the functionality across the scripts.

Creating a reoccurring function, allows for a consistent understanding of the automation behaviour and consistency across the script.


Reusing Functions Within Functions

The use case requires the 'drop down' functionality, and as this is likely to be repeated in further use cases, it makes sense to build this out as a reusable function.

Breaking down the UI interaction, a user would move to the menu and select an option from the dropdown - which can be partially facilitated using the navigate function already created.

Drop Down Function:Calling the Function:
to dropDown menu, action, validation
moveto text:menu
wait 1
navigate (action),(validation)
end dropDown
dropDown ("Computers"),("Desktops"),("Categories")

Using the functions like 'Lego', accelerates the generation of the framework.


Simplifying Approaches

The final function is to 'launch a browser' to the webpage. While this is being only called once in the example use case - it may be that a broader requirement is cross browser testing or the use cases may lead to other webpages.

For that, we've built a function for launching a browser and parameterised the browser and url:

Original Launch Browser Function:Calling the Function:
to launchBrowser browser,url
click image:"icons/"&browser
waitfor 20, image:"icons/refresh" //icon
typetext url,returnkey
waitfor 20, image:"logos" //Logo
end launchBrowser
launchBrowser ("chrome"),("https://demo.nopcommerce.com/")

Simpler / Cheaper Alternatives To Scripts

Outside our rules of thumb, it is good practice to look back and ensure any function is the simplest it could be.

Key aspects to consider are:
  • What if the SUT / AUT change.
  • What if we need to extend the test pack - Will the approach need adapting / will it need updating or extending?
  • How can we avoid capturing test assets of the system not involved in testing i.e. Operating System UIs / Browser UIs etc.

A good example of this is the Launch Browser Script. Currently to run this against chrome, we have caught an image of the Chrome Icon, we then validate Chrome has launched by capturing the refresh button.

What if we wanted to include extend the testing to Firefox and Edge? We would require 4 new images to be captured(icons and refresh buttons per browser). This may seem like a small overhead, however if this function represents the overall approach we've taken, then it would suggest a high maintenance cost which is easily avoidable.

A solution would be to utilise built in SUT functionality, like the 'Windows Run' window and launch the Browser straight to the URL and validate with the AUT logo, in this case the NopCommerce logo.

Here we have significantly reduced the number of test assets (browser icon and browser refresh button) captured outside the test scope.

Original Launch Browser FunctionUpdated Launch Browser Function
to launchBrowser browser,url
click image:"icons/"&browser
waitfor 20, image:"icons/refresh" //icon
typetext url,returnkey
waitfor 20, image:"logos" //Logo
end launchBrowser
to launchBrowser browser,url
typetext windowskey, "r" // launch Run window
wait 1
typetext browser && url, returnkey
waitfor 20, image:"logos" // Logo
end launchBrowser

A Summary of What You Have Learned

A fundamental best practice of automation development, is to ensure that the scripts are as modular and reusable as possible. Grouping reoccurring functionality and simplifying the code using parameters ensure that the scripts are more maintainable.

Bad Practice Example
Good Practice Example
Testcase:

// Step 1
click image:"chrome" // Icon
waitfor 20, image:"refresh" // Icon

set the searchRectangle to (0,70,1920,1039) // Optimises OCR
typetext "https://demo.nopcommerce.com/",returnkey
waitfor 20, image:"nopCommerce" // Logo

// Step 2
moveto text:"Computers"
wait 1 // Optimises OCR
click text:"Desktops"
wait 1.5 // Optimises OCR
waitfor 20, text:"Categories"

// Step 3
click text:"Digital Storm VANQUISH 3"
wait 1.5 // Optimises OCR
waitfor 20, text:"Digital Storm Vanquish 3 Desktop PC"

// Step 4
click text:"ADD TO CART"
wait 2 // Optimises OCR
waitfor 20,text:"The product has been added to your shopping cart"

// Step 5
moveto image:"Basket"
wait 1
click text:"GO TO CART"
wait 2 // Optimises OCR
waitfor 20, text:"Shopping Cart"
assert that imagefound(0,text:"Digital Storm VANQUISH 3 Custom Performance PC")

Testcase:
// Step 1
launchBrowser ("chrome"),("https://demo.nopcommerce.com/")
set the searchRectangle to (0,70,1920,1039)
// Step 2
dropDown ("Computers"),("Desktops"),("Categories")
// Step 3
navigate ("Digital Storm VANQUISH 3"),("Digital Storm Vanquish 3 Desktop PC")
// Step 4
navigate ("ADD TO CART"),("The product has been added to your shopping cart")
// Step 5
dropDown ("Shopping cart"),("GO TO CART"),("Shopping Cart")
// END
Methods / Functions:
// function to launch browser
to launchBrowser browser,url
set global browser to browser
typetext windowskey,"r"
wait 1
typetext browser&&url,returnkey
waitfor 20, image:"logos" // LOGO
end launchBrowser

// function that moves to and initiates dropdown
to dropDown menu,action,validation
moveto text:menu,searchRectangle:config().browser.(global browser)
wait 1
navigate (action),(validation)
end dropDown

// function to navigate using action and validation framework
to navigate action,validation
click text:action,searchRectangle:config().browser.(global browser)
wait 1.5 // page transition
waitfor 20, text:validation,searchRectangle:config().browser.(global browser)
end navigate
Images Folder:

Images Folder: