Are there any general guidelines which demonstrate the difficulty of automating the front end of a web app?
For example, one such guideline could be that all "critical" elements have ID attributes whose values don't change frequently. Are there any other guidelines like this?
This is a very tricky question indeed. I'll give it a shot, but mind you I'm barely going to scratch the surface with this.
Disclaimer: What I've written now, especially considering the speed with which the web is moving forward/changing (new W3C standards, new frameworks, new levels of abstraction over the same old programming principles), might very well be obsolete or bad-practice in a few years.
- WebElement locators (my personal take on the matter)
When you gave the example of changing ids
& classes
I can't deny I rolled my eyes a bit. But you gave us the first classification:
QA Automation Engineers that have commit rights on Production Code:
We are in the 21st century, in the most technologically progressive era of human-kind and we still feel we should keep the commit rights off-limits for our QAs. Damn!
The QA Automation team SHOULD create their own set of automation attributes in accordance to a previously well thought-out & documented strategy.
The QA Automation team SHOULD have the possibility to add/remove/change IDs
, classes
, attributes
in the PROD code, as required by their automation agenda.
Your WebElement
mappings SHOULD look like this (this is from a CucumberJS
elements module I wrote):
'Device Details of Android phone':'li[connectqa-device="android-phone"] a.detail-button',
'Device Details of Android tablet':'li[connectqa-device="android-tablet"] a.detail-button',
'Device Details of iOS phone':'li[connectqa-device="ios-phone"] a.detail-button',
'Device Details of iOS tablet':'li[connectqa-device="ios-tablet"] a.detail-button',
'Device Details of Windows laptop':'li[connectqa-device="windows-laptop"] a.detail-button',
'Device Details of Windows PC':'li[connectqa-device="windows-pc"] a.detail-button',
The above WebElements
have the following qualities: homogeneous, optimized (no more than 2 tags chained), scalable, dynamic (the connectqa-device
attribute's value is generated by { deviceType }
in an ng-repeat
(Angular web app)), easy to identify/use when writing automated test-cases due to the obvious scheme.
Your WebElement
mappings SHOULDN'T look like this:
'add friend email input error mark':'#scroller-bulk-invite div.form-group.mb10.wrapper.email-f.error div.invalid',
'add friend name input error mark':'#scroller-bulk-invite div.form-group.wrapper.name-f.error div.invalid',
'plus button':'#statusStaging div.staging-holder div.devices-staging.ng-isolate-scope ul.actions li'
QA Automation Engineers that only have access to the Live Code:
Here we come to a new pitchfork: do your DEVs want to implement the WebElement
attributes strategy that your previously thought-out & documented?
If NO, then you can either try your best to create the best WebElement
locator strategy with what you have at your disposal.
If YES, then we're in luck. Someone just took a big burden off your shoulders. Now you can concentrate on other things, like optimizing that automation harness.
- Web Frameworks (especially JS ones)
Most web frameworks nowadays pump a lot of logic into the HTML via different directives/components/decorators/etc. Some of these will be visible to you at different times of the automated test running, or all-throughout the test execution.
!!! Note: I greatly encourage you to stay away from these when creating your WebElement
mappings. You are exposing yourself to the following:
$( document ).ready()
marker. If you don't have serious explicit/implicit waiting in your methods, expect some serious flakiness in your tests);'Element not found' errors (These directives/components/decorators in today's frameworks are very prone to change. DEVs might just add/change/remove a specific one which you were referring in your mappings and PUUUFF!, your regression goes to s@%&.)
Example: (Angular) .ng-scope
, .ng-if
, .ng-click
, etc. These should NEVER be in your WebElement
locator. Else, you're just asking for it!
To be continued ...