genevish
genevish

Reputation: 111

Getting XML node matching XPath expression

I'm hoping you can help with this. I tried a number of XPath testers online and wasn't able to find a solution.

I'm trying to get the value of the first node with the '~tid' attribute from this XML:

<Response status="ok" version="1.1">
                 <Action>
                    <Page>
                       <Params>
                          <Param name="~tid" value="1345811517165"/>
                          <Param name="~action-type" value="DATA"/>
                          <Param name="~from-page" value="login"/>
                          <Param name="~from-act" value="submitData"/>
                          <Param name="login_USERNAME" value="" type="0"/>
                          <Param name="login_PASSWORD" value="" type="0"/>
                       </Params>
                    </Page>
                    <Data name="clientData" method="POST">
                       <Params>
                          <Param name="timezoneoffset" value=""/>
                          <Param name="daylightsavings" value=""/>
                       </Params>
                    </Data>
                 </Action>
                 <Action>
                    <Page>
                       <Params>
                          <Param name="~tid" value="1345811517165"/>
                          <Param name="~action-type" value="NAV"/>
                          <Param name="~from-page" value="login"/>
                          <Param name="~from-act" value="resetPassword"/>
                          <Param name="~to-page" value="login_resetPassword"/>
                       </Params>
                    </Page>
                 </Action>
                 <Action>
                    <Page>
                       <Params>
                          <Param name="~tid" value="1345811517165"/>
                          <Param name="~action-type" value="NAV"/>
                          <Param name="~from-page" value="login"/>
                          <Param name="~from-act" value="newUser"/>
                          <Param name="~to-page" value="login_newUser"/>
                       </Params>
                    </Page>
                 </Action>
</Response>

The XPath I'm using is:

//Params[1]/Param[@name='~tid']/@value

It gets all three values. How can I get just the first one?

Upvotes: 2

Views: 348

Answers (2)

Dimitre Novatchev
Dimitre Novatchev

Reputation: 243459

This is the second most FAQ in XPath.

Use:

(//Params/Param[@name='~tid'])[1]/@value 

Or even:

(//Param[@name='~tid'])[1]/@value 

Explanation:

The XPath pseudo-operator // has lower precedence (priority) than the [] operator.

The usual solution in any laguage when default priority needs to be overriden is to use brackets that explicitly specify the new, wanted priorities.

Upvotes: 0

O. R. Mapper
O. R. Mapper

Reputation: 20710

Try

/descendant::Params[1]/Param[@name='~tid']/@value

From the W3C XPath specification:

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.

Upvotes: 1

Related Questions