This Tutorial Explains XPath Axes for Dynamic XPath in Selenium WebDriver With the help of Various XPath Axes Used, Examples and Explanation of Structure:
In the previous tutorial, we have learned about XPath functions and its importance in identifying the element. However, when more than one elements have too similar orientation and nomenclature, it becomes impossible to identify the element uniquely.
=> Check Out The Perfect Selenium Training Guide Here.
Table of Contents:
Understanding XPath Axes
Let us understand the above-mentioned scenario with the help of an example.
Think about a scenario where two links with “Edit” text are used. In such cases, it becomes pertinent to understand the nodal structure of the HTML.
Please copy-paste the below code into notepad and save it as .htm file.
<!DOCTYPE html> <html> <body> <div class="1" align="left"> <a href="">Edit</a> <div class="2" align="left"> <a href="">Edit</a> </div> </body> </html>
The UI will look like the below screen:
Problem Statement
Q #1) What to do when even XPath Functions fail to identify the element?
Answer: In such a case, we make use of the XPath Axes along with XPath Functions.
The second part of this article deals with how we can use the hierarchical HTML format to identify the element. We will start by getting a little information on the XPath Axes.
Q #2) What are XPath Axes?
Answer: An XPath axes define the node set relative to the current (context) node. It is used to locate the node that is relative to the node on that tree.
Q #3) What is a Context Node?
Answer: A context node can be defined as the node the XPath processor is currently looking at.
Different XPath Axes Used In Selenium Testing
There are thirteen different axes that are listed below. However, we’re not going to use all of them during Selenium testing.
- ancestor: These axes indicate all the ancestors relative to the context node, also reaching up to the root node.
- ancestor-or-self: This one indicates the context node and all the ancestors relative to the context node, and includes the root node.
- attribute: This indicates the attributes of the context node. It can be represented with the “@” symbol.
- child: This indicates the children of the context node.
- descendent: This indicates the children, grandchildren, and their children (if any) of the context node. This does NOT indicate the Attribute and Namespace.
- descendent-or-self: This indicates the context node and the children, and grandchildren and their children (if any) of the context node. This does NOT indicate the attribute and namespace.
- following: This indicates all the nodes that appear after the context node in the HTML DOM structure. This does NOT indicate descendent, attribute, and namespace.
- following-sibling: This one indicates all the sibling nodes (same parent as the context node) that appear after the context node in the HTML DOM structure. This does NOT indicate descendent, attribute, and namespace.
- namespace: This indicates all the namespace nodes of the context node.
- parent: This indicates the parent of the context node.
- preceding: This indicates all the nodes that appear before the context node in the HTML DOM structure. This does NOT indicate descendent, attribute, and namespace.
- preceding-sibling: This one indicates all the sibling nodes (same parent as the context node) that appear before the context node in the HTML DOM structure. This does NOT indicate descendent, attribute, and namespace.
- self: This one indicates the context node.
Structure Of XPath Axes
Consider the below hierarchy for understanding how the XPath Axes work.
Refer below to a simple HTML code for the above example. Please copy-paste the below code into the Notepad editor and save it as a .html file.
<!DOCTYPE html> <html> <body> <div class="Animal" align="center"> <h2>Animal</h2> <div class="Vertebrate" align="left" > <h3 align="left">Vertebrate</h3> <div class="Fish" white-space=:pre> <h4 >Fish</h4> </div> <div class="Mammal"> <h4>Mammal</h4> <div class="Herbivore"> <h5>Herbivore</h5> </div> <div class="Carnivore"> <h5>Carnivore</h5> <div class="Lion"> <h6>Lion</h6> </div> <div class="Tiger"> <h6>Tiger</h6> </div> </div> </div> <div class="Other"> <h4>Other</h4> </div> </div> <div class="Invertebrate"> <h3>Invertebrate</h3> <div class="Insect"> <h4>Insect</h4> </div> <div class="Crustacean"> <h4>Crustacean</h4> </div> </div> </div> </body> </html>
The page will look like the one below. Our mission is to make use of the XPath Axes to find the elements uniquely. Let’s try to identify the elements that are marked in the chart above. The context node is “Mammal”
#1) Ancestor
Agenda: To identify the ancestor element from the context node.
XPath#1: //div[@class=’Mammal’]/ancestor::div
The XPath “//div[@class=’Mammal’]/ancestor::div” throws two matching nodes:
- Vertebrates, as it is the parent of “Mammal”, hence it is considered the ancestor too.
- Animal as it the parent of the parent of “Mammal”, hence it is considered an ancestor.
Now, we only need to identify one element which is the “Animal” class. We can use the XPath as mentioned below.
XPath#2: //div[@class='Mammal']/ancestor::div[@class='Animal']
If you want to reach the text “Animal”, below XPath can be used.
#2) Ancestor-or-self
Agenda: To identify the context node and the ancestor element from the context node.
XPath#1: //div[@class=’Mammal’]/ancestor-or-self::div
The above XPath#1 throws three matching nodes:
- Animal(Ancestor)
- Vertebrate
- Mammal(Self)
#3) Child
Agenda: To identify the child of context node “Mammal”.
XPath#1: //div[@class=’Mammal’]/child::div
XPath#1 helps to identify all the children of context node “Mammal”. If you want to get the specific child element, please use XPath#2.
XPath#2: //div[@class=’Mammal’]/child::div[@class=’Herbivore’]/h5
#4) Descendent
Agenda: To identify the children and grandchildren of the context node (for instance: ‘Animal’).
XPath#1: //div[@class=’Animal’]/descendant::div
As the Animal is the top member of the hierarchy, all the child and descendant elements are highlighted. We can also change the context node for our reference and use any element we want as the node.
#5) Descendant-or-self
Agenda: To find the element itself, and its descendants.
XPath1: //div[@class=’Animal’]/descendant-or-self::div
The only difference between descendent and descendent-or-self is that it highlights itself in addition to highlighting the descendants.
#6) Following
Agenda: To find all the nodes that follow the context node. Here, the context node is the div that contains the Mammal element.
XPath: //div[@class=’Mammal’]/following::div
In the following axes, all the nodes that follow the context node, be it the child or descendant, are getting highlighted.
#7) Following-sibling
Agenda: To find all the nodes after the context node that share the same parent, and are a sibling to the context node.
XPath: //div[@class=’Mammal’]/following-sibling::div
The major difference between the following and following siblings is that the following sibling takes all the sibling nodes after the context but will also share the same parent.
#8) Preceding
Agenda: It takes all the nodes that come before the context node. It may be the parent or the grandparent node.
Here the context node is Invertebrate and highlighted lines in the above image are all the nodes that come before the Invertebrate node.
#9) Preceding-sibling
Agenda: To find the sibling that shares the same parent as the context node, and that comes before the context node.
As the context node is the Invertebrate, the only element that is being highlighted is the Vertebrate as these two are siblings and share the same parent ‘Animal’.
#10) Parent
Agenda: To find the parent element of the context node. If the context node itself is an ancestor, it won’t have a parent node and will fetch no matching nodes.
Context Node#1: Mammal
XPath: //div[@class=’Mammal’]/parent::div
As the context node is Mammal, the element with Vertebrate is getting highlighted as that is the parent of the Mammal.
Context Node#2: Animal
XPath: //div[@class=’Animal’]/parent::div
As the animal node itself is the ancestor, it won’t highlight any nodes, and hence No Matching nodes were found.
#11) Self
Agenda: To find the context node, the self is used.
Context Node: Mammal
XPath: //div[@class=’Mammal’]/self::div
As we can see above, the Mammal object has been identified uniquely. We can also select the text “Mammal by using the below XPath.
XPath: //div[@class=’Mammal’]/self::div/h4
Uses Of Preceding And Following Axes
Suppose you know that your target element is how many tags are ahead or back from the context node, you can directly highlight that element and not all the elements.
Example: Preceding (with index)
Let’s assume our context node is “Other” and we want to reach the element “Mammal”, we would use the below approach to do so.
First Step: Simply use the preceding without giving any index value.
XPath: //div[@class=’Other’]/preceding::div
This gives us 6 matching nodes, and we want only one targeted node “Mammal”.
Second Step: Give the index value[5] to the div element(by counting upwards from the context node).
XPath: //div[@class=’Other’]/preceding::div[5]
In this way, the “Mammal” element has been identified successfully.
Example: following (with index)
Let’s assume our context node is “Mammal” and we want to reach the element “Crustacean”, we will use the below approach to do so.
First Step: Simply use the following without giving any index value.
XPath: //div[@class=’Mammal’]/following::div
This gives us 4 matching nodes, and we want only one targeted node “Crustacean”
Second Step: Give the index value[4] to the div element(count ahead from the context node).
XPath: //div[@class=’Other’]/following::div[4]
This way the “Crustacean” element has been identified successfully.
The above scenario can also be re-created with preceding-sibling and following-sibling by applying the above approach.
Conclusion
Object Identification is the most crucial step in the automation of any website. If you can acquire the skill to learn the object accurately, 50% of your automation is done. While there are locators available to identify the element, there are some instances where even the locators fail to identify the object. In such cases, we must apply different approaches.
Here we have used XPath Functions and XPath Axes to uniquely identify the element.
We conclude this article by jotting down a few points to remember:
- You shouldn’t apply “ancestor” axes on the context node if the context node itself is the ancestor.
- You shouldn’t apply “parent” axes on the context node of the context node itself as the ancestor.
- You shouldn’t apply “child” axes on the context node of the context node itself as the descendant.
- You shouldn’t apply “descendant” axes on the context node of the context node itself as the ancestor.
- You shouldn’t apply “following” axes on the context node it’s the last node in the HTML document structure.
- You shouldn’t apply “preceding” axes on the context node it’s the first node in the HTML document structure.
Happy Learning!!!
=> Visit Here For The Exclusive Selenium Training Tutorial Series.