xquery filter on attribute and element

general exception picture general exception · Jul 5, 2012 · Viewed 21.7k times · Source

I have the following simple XML document:

<?xml version="1.0" encoding="UTF-8"?>
<cars>
    <car>
        <data attrib="Make">
            <text>Volvo</text>
        </data>
        <data attrib="Model">
            <text>855</text>
        </data>
    </car>
    <car>
        <data attrib="Make">
            <text>Volvo</text>
        </data>
        <data attrib="Model">
            <text>745</text>
        </data>
    </car>
    <car>
        <data attrib="Make">
            <text>Volvo</text>
        </data>
        <data attrib="Model">
            <text>V70R</text>
        </data>
    </car>
</cars>

And the following XPath:

/cars/car/data[(@attrib='Model') and (text='855')]

This returns the following result:

<data attrib="Model"><text>855</text></data>

I want the XPath to return the whole <car> block for the match.

So return data would be like this:

<cars>
    <car>
        <data attrib="Make">
            <text>Volvo</text>
        </data>
        <data attrib="Model">
            <text>855</text>
        </data>
    </car>
</cars>

How would I modify the XPath expression above to achieve this?

Answer

Mitya picture Mitya · Jul 5, 2012

XPath returns whatever node you go up to - in your case you're going to data, so that's what you're getting back. If you want car instead, place your predicate after car.

/cars/car[data/@attrib='Model' and data/text='855']

Or, slightly shorter

/cars/car[data[@attrib='Model' and text='855']]

You can run it at this XMLPlayground.

XQuery to produce the desired output:

<cars>
  {/cars/car[data[@attrib='Model' and text='855']]}
</cars>