How to access second element using relative Xpath

5.2k views Asked by At

Given this page snippet

<section id="mysection">
    <div>
        <div>
            <div>
                <a href="">
                <div>first</div>
                </a>
            </div>
            <div>
                <a href="">
                <div>second</div>
                </a>
            </div>
        </div>
    </div>
</section>

I want to access the second a-element using relative Xpath. In FF (and locating with Selenium IDE) this

//section[@id='mysection']//a[1]

works but this does not match

//section[@id='mysection']//a[2]

What is wrong with the second expression?

EDIT: Actually I do not care so much about Selenium IDE (just use it for quick verification). I want to get it going with selenium2library in Robot Framework. Here, the output is:

ValueError: Element locator with prefix '(//section[@id' is not supported

for the suggested solution (//section[@id='mysection']//a)[2]

4

There are 4 answers

1
mkanugan On BEST ANSWER

You can use this. This would select the anchor descendants of section and get you the second node. This works with xslt processor, hope this works with Selenium

//section[@id='mysection']/descendant::a[2]
4
har07 On

Try this way instead :

(//section[@id='mysection']//a)[2]

//a[2] looks for <a> element within the same parent. Since each parent <div> only contains one <a> child, your xpath didn't match anything.

1
Kudin On

With this:

//section[@id='mysection']//a[1]

you are matching all first 'a' elements within any context (inside one div, for example), but with this

//section[@id='mysection']//a[2]

you are trying to match any second 'a' element with any context, but you dont have more than one 'a' element in any of nodes. The icrementing sibling node thus should be a parent div node to those 'a' tags.

Very simple:

//section[@id='mysection']//a[1] - both elements

This is why previous answer with paranthesis around the whole thing is correct.

//section[@id='mysection']//div[1]/a - only first element
//section[@id='mysection']//div[2]/a - only second elemnt

Other way to mach each 'a' separately:

//section[@id='mysection']//a[div[text()='first']]
//section[@id='mysection']//a[div[text()='second']]
0
Manu On

Other ways to reach to the second a-element can be by using the

<div>second</div>, call this bottom-up approach

instead of starting from section-element

<section id="mysection">, call this top-down approach

Using the div child of a-element, the solutions should look like this:

//div[.='second']/..