views:

751

answers:

3

I'm trying to parse XML returned from the Youtue API. The APIcalls work correctly and creates an XmlDocument. I can get an XmlNodeList of the "entry" tags, but I'm not sure how to get the elements inside such as the , , etc...

 XmlDocument xmlDoc = youtubeService.GetSearchResults(search.Term, "published", 1, 50);
 XmlNodeList listNodes = xmlDoc.GetElementsByTagName("entry");
 foreach (XmlNode node in listNodes)
 {
     //not sure how to get elements in here
 }

The XML document schema is shown here: http://code.google.com/apis/youtube/2.0/developers_guide_protocol_understanding_video_feeds.html

I know that node.Attributes is the wrong call, but am not sure what the correct one is?

By the way, if there is a better way (faster, less memory) to do this by serializing it or using linq, I'd be happy to use that instead.

Thanks for any help!

+3  A: 

Here some examples reading the XmlDocument. I don't know whats fastest or what needs less memory - but i would prefer Linq To Xml because of its clearness.

XmlDocument xmlDoc = youtubeService.GetSearchResults(search.Term, "published", 1, 50);
XmlNodeList listNodes = xmlDoc.GetElementsByTagName("entry");
foreach (XmlNode node in listNodes)
{
    // get child nodes
    foreach (XmlNode childNode in node.ChildNodes)
    {
    }

    // get specific child nodes
    XPathNavigator navigator = node.CreateNavigator();
    XPathNodeIterator iterator = navigator.Select(/* xpath selector according to the elements/attributes you need */);

    while (iterator.MoveNext())
    {
     // f.e. iterator.Current.GetAttribute(), iterator.Current.Name and iterator.Current.Value available here
    }
}

and the linq to xml one:

XmlDocument xmlDoc = youtubeService.GetSearchResults(search.Term, "published", 1, 50);
XDocument xDoc = XDocument.Parse(xmlDoc.OuterXml);
var entries = from entry in xDoc.Descendants("entry")
        select new
        {
         Id = entry.Element("id").Value,
         Categories = entry.Elements("category").Select(c => c.Value)
        };

foreach (var entry in entries)
{
    // entry.Id and entry.Categories available here
}
n26
Thanks! That really clears it up.
rksprst
A: 

You could use XSD.exe to generate a class based on the schema provided. Once generated, you could then parse the XML response into the strongly typed class.

string xmlResponse = GetMyYouTubeStuff();
MyYouTubeClass response = null;
XmlHelper<MyYouTubeClass> xmlHelper = new XmlHelper<MyYouTubeClass>();
response = xmlHelper.Deserialize(xmlResponse);

And the class for deserializing it...

public class XmlHelper<T>
{
 public T Deserialize(string xml)
  {
    XmlSerializer xs = new XmlSerializer(typeof(T));

    Byte[] byteArray = new UTF8Encoding().GetBytes(xml);
    MemoryStream memoryStream = new MemoryStream(byteArray);

    XmlTextReader xmlTextReader = new XmlTextReader(memoryStream);

    T retObj = (T)xs.Deserialize(xmlTextReader);

    return retObj;
  }
}

There's also another way here.

Dan Atkinson
+1  A: 

I realise this has been answered and LINQ to XML is what I'd go with but another option would be XPathNavigator. Something like

XPathNavigator xmlNav = xmlDoc.CreateNavigator();
XPathNodeIterator xmlitr = xmlNav.Select("/XPath/expression/here")

while (xmlItr.MoveNext()) ...

The code is off the top of my head so it may be wrong and there may be a better way with XPathNavigator but it should give you the general idea

Kevin Jones