tags:

views:

648

answers:

1

Hello,

I have an issue. I have hierarchical XML data such as:

<Tree>
  <Node Text="Stuff" ItemGUID="064a9bf0-0594-47f8-87be-88dd73763c77" >
    <Node Text="Food" ItemGUID="326f1f7a-d364-4838-9bdc-ce5fd93f88ca" ItemType="2" />
    <Node Text="Wines" ItemGUID="950e3ca3-27a1-41fd-89f3-7a8b08633a9f" />
    <Node Text="Flowers" ItemGUID="cefa8c34-af06-48e7-9c00-4b1422d217a4">
        <Node Text="Roses" ItemGUID="950e3ca3-27a1-41fd-89f3-7a8b08633a9f">
              <Node Text="Red" ItemGUID="950e3ca3-27a1-41fd-89f3-7a8b08633a9f" />
              <Node Text="Pink" ItemGUID="950e3ca3-27a1-41fd-89f3-7a8b08633a9f" />
              <Node Text="White" ItemGUID="950e3ca3-27a1-41fd-89f3-7a8b08633a9f" />
        </Node>
        <Node Text="Tulips" ItemGUID="950e3ca3-27a1-41fd-89f3-7a8b08633a9f" />
        <Node Text="Whatever" ItemGUID="950e3ca3-27a1-41fd-89f3-7a8b08633a9f" />
    </Node>
    <Node Text="Sweet Delights" ItemGUID="1df7dbae-adf0-49a9-aaac-1358468a245b" />
  </Node>
</Tree>

And I need to get just Flowers (Roses, Tulips, Whatever) WITHOUT Red, Pink, White (under Roses) I'm using the following code, but due to the fact that all nodes are "Node" I get all levels of Descendats. I would like to limit it to only one level.

XElement loadedXML = clients.ItemTreeXML;

//filter only current node
XElement procXML;
procXML = new XElement ("Tree",
          from el in loadedXML.Descendants("Node")
          where (string)el.Attribute("ItemGUID") == currentNodeGUID
          select el);

Result Wanted:

<Tree>
        <Node Text="Flowers" ItemGUID="cefa8c34-af06-48e7-9c00-4b1422d217a4">
            <Node Text="Roses" ItemGUID="950e3ca3-27a1-41fd-89f3-7a8b08633a9f" />
            <Node Text="Tulips" ItemGUID="950e3ca3-27a1-41fd-89f3-7a8b08633a9f" />
            <Node Text="Whatever" ItemGUID="950e3ca3-27a1-41fd-89f3-7a8b08633a9f" />
        </Node>
</Tree>

Thanks,

Added: Maybe a SQL 2008 query could retreive only the node branch I need, but after lots of research and testing, I could not find an answer... (My XML is in a XML column in SQL 2008)

A: 

So we have this...

XElement loadedXML = XElement.Load("test.xml");

//filter only current node
XElement procXML;
procXML = new XElement("Tree",
    from el in loadedXML.Descendants("Node")
    where (string)el.Attribute("ItemGUID") == currentNodeGUID
    select el);

Best way I found was to remove all the child elements after you do the LINQ query. Like this:

foreach (XElement xl in procXML.Element("Node").Elements("Node"))
{
    if (xl.HasElements) // just remove the ones without child elements
    {
        xl.RemoveNodes();
    }
}

That will output what you have desired, but I must add... There is most definately a better way to do this. I don't know how well it will work with your situation given most code written needs to work more dynamically than this.

I saw this question and decided to take a dive into Linq, I guess it wasn't that bad. If that doesn't work just the way it needs to, at least it's a start.

Zach Howe
Thanks for input. I was doing the same thing. Just wondering is there is a quicker way. Optionnally a SQL 2008 XML query would be great but I can't find any way to get only the node set I need. I would like to avoid loading into ram huge XML when in reality I just need one of the many branches, and only one level of this branch.
mfr