kbaccouche kbaccouche - 8 days ago 6
C# Question

XDocument get XML element by the value of its name attribute

I have an

XML
result like this

<response>
<lst name="responseHeader">
<int name="status">0</int>
<int name="QTime">16</int>
</lst>
<result name="response" numFound="3" start="0" maxScore="1.0">
<doc>
<str name="ContaFirstname">
firstname1
</str>
<str name="ContaId">6557</str>
<str name="ContaJobTitle">Manager</str>
<str name="ContaSurname">surname1
</str>
</doc>
<doc>
<str name="ContaFirstname">firstname2</str>
<str name="ContaId">6203</str>
<str name="ContaJobTitle">Director</str>
<str name="ContaSurname">surname2</str>
</doc>
</result>
</response>


I want to get a list of objects, and every object will contain the value of
ContaFirstname
,
ContaId
,
ContaJobTitle
and
ContaSurname


I tried something like this, but that's not right because I get them all NULL

var test = from c in xml.Descendants("doc")
select new
{
firstname = c.Element("ContaFirstname"),
surnmane = c.Element("ContaSurname")
};


So how can access these elements by name?

Answer

You don't want to access the elements by name as most people would interpret that statement. You want to access the elements by the value of their name attribute:

firstname = (string) c.Elements("str")
                      .First(x => x.Attribute("name").Value == "ContaFirstname");
//etc

You may well want to abstract that into a separate method, as it's going to be a pain to do it multiple times. For example:

public static XElement ElementByNameAttribute(this XContainer container,
                                              string name)
{
    return container.Elements("str")
                    .First(x => x.Attribute("name").Value == name);
}

Then:

var test = from c in xml.Descendants("doc")
           select new 
           { 
               firstname = c.ElementByNameAttribute("ContaFirstname").Value,
               surnmane = c.ElementByNameAttribute("ContaSurname").Value
           }; 

If you have any chance to give your document a more sensible structure, that would be preferable...