What if I had a document that had multiple elements with the same name -- how would I retrieve, for instance, the second element?
<doc>
...
<element name="same">foo</element>
...
<element name="same">bar</element>
...
<element name="same">baz</element>
...
</doc>
I'd expect something like //elem[@name='same'][2] to work.
Additionally, how would I find the second from last element in xpath with a variable number of elements with the same name
If an xpath refers multiple elements on the DOM, It should be surrounded by brackets first () and then use numbering. if the xpath refers 4 elements in DOM and you need 3rd element then working xpath is (common xpath)[3].
For example if both text fields have //input[@id='something'] then you can edit the first field xpath as (//input[@id='something'])[1] and the second field's xpath as (//input[@id='something'])[2] in object repository.
We can create an xpath for their identification and utilize the method find_elements_by_xpath. With this, the elements with the matching value of the given xpath are returned in the form of a list. In case there is no element with the matching value of the xpath, an empty list shall be returned.
you just have to click the Elements tab and press Ctrl + F to open a search box in chrome developer tool. On inspecting the web element, you can see it has an input tag and attributes like class and id. So you can write XPath and it will try to search based on that criteria.
[ ]
has higher priority than // (and "//" is actually only an abbreviation, not an operator). This is so, because according to the XPath 1.0 Spec,
"// is short for /descendant-or-self::node()/"
and later:
"NOTE: The location path //para[1]
does not mean the same as the location path /descendant::para[1]
. The latter selects the first descendant para element; the former selects all descendant para elements that are the first para children of their parents."
Therefore, the XPath expression:
//element[@name='same'][2]
means:
Select any element in the document, that is named "element", has an attribute "name" with value "same", and this element is the second such child of its parent.
What you want is:
(//element[@name='same'])[2]
Note the brackets, which override the higher precedence of [].
Similarly, the last but one such node is selected by the following XPath expression:
(//element[@name='same'])[last()-1]
Finally, a necessary warning: The use of the "//" abbreviation is very expensive as it causes the whole (sub)tree to be traversed. Whenever the structure of the document is known, it is recommended to use more specific constructs (location paths).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With