What is the correct XPath for choosing attributes that contain "foo"?

XmlXpath

Xml Problem Overview


Given this XML, what XPath returns all elements whose prop attribute contains Foo (the first three nodes):

<bla>
 <a prop="Foo1"/>
 <a prop="Foo2"/>
 <a prop="3Foo"/>
 <a prop="Bar"/>
</bla>

Xml Solutions


Solution 1 - Xml

//a[contains(@prop,'Foo')]

Works if I use this XML to get results back.

<bla>
 <a prop="Foo1">a</a>
 <a prop="Foo2">b</a>
 <a prop="3Foo">c</a>
 <a prop="Bar">a</a>
</bla>

Edit: Another thing to note is that while the XPath above will return the correct answer for that particular xml, if you want to guarantee you only get the "a" elements in element "bla", you should as others have mentioned also use

/bla/a[contains(@prop,'Foo')]

This will search you all "a" elements in your entire xml document, regardless of being nested in a "blah" element

//a[contains(@prop,'Foo')]  

I added this for the sake of thoroughness and in the spirit of stackoverflow. :)

Solution 2 - Xml

This XPath will give you all nodes that have attributes containing 'Foo' regardless of node name or attribute name:

//attribute::*[contains(., 'Foo')]/..

Of course, if you're more interested in the contents of the attribute themselves, and not necessarily their parent node, just drop the /..

//attribute::*[contains(., 'Foo')]

Solution 3 - Xml

descendant-or-self::*[contains(@prop,'Foo')]

Or:

/bla/a[contains(@prop,'Foo')]

Or:

/bla/a[position() <= 3]

Dissected:

descendant-or-self::

The Axis - search through every node underneath and the node itself. It is often better to say this than //. I have encountered some implementations where // means anywhere (decendant or self of the root node). The other use the default axis.

* or /bla/a

The Tag - a wildcard match, and /bla/a is an absolute path.

[contains(@prop,'Foo')] or [position() <= 3]

The condition within [ ]. @prop is shorthand for attribute::prop, as attribute is another search axis. Alternatively you can select the first 3 by using the position() function.

Solution 4 - Xml

John C is the closest, but XPath is case sensitive, so the correct XPath would be:

/bla/a[contains(@prop, 'Foo')]

Solution 5 - Xml

If you also need to match the content of the link itself, use text():

//a[contains(@href,"/some_link")][text()="Click here"]

Solution 6 - Xml

Have you tried something like:

//a[contains(@prop, "Foo")]

I've never used the contains function before but suspect that it should work as advertised...

Solution 7 - Xml

/bla/a[contains(@prop, "foo")]

Solution 8 - Xml

try this:

//a[contains(@prop,'foo')]

that should work for any "a" tags in the document

Solution 9 - Xml

For the code above... //*[contains(@prop,'foo')]

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
Questionripper234View Question on Stackoverflow
Solution 1 - XmlevilhomerView Answer on Stackoverflow
Solution 2 - XmlAlex BeynensonView Answer on Stackoverflow
Solution 3 - Xml1729View Answer on Stackoverflow
Solution 4 - XmlMetro SmurfView Answer on Stackoverflow
Solution 5 - XmlSomeDudeSomewhereView Answer on Stackoverflow
Solution 6 - XmltoddkView Answer on Stackoverflow
Solution 7 - XmlDavid HillView Answer on Stackoverflow
Solution 8 - XmlDani DuranView Answer on Stackoverflow
Solution 9 - XmldigiguruView Answer on Stackoverflow