Search code examples
c#xmlxpathxmldocument

Read XML by xpath containing namespace prefix


im trying to read from this http://api.hostip.info/?ip=12.215.42.19

XmlDocument xml = new XmlDocument();

xml.Load("http://api.hostip.info/?ip=79.177.176.8");

XmlNodeList xnList = xml.SelectNodes("gml:featureMember/Hostip");
foreach (XmlNode xn in xnList)
{
    string Name = xn["countryName"].InnerText;
    MessageBox.Show(Name);
}

im getting a weird error

Namespace Manager or XsltContext needed. This query has a prefix, variable, or user-defined function.

never seen something like that before...


Solution

  • You need to, first, define mapping of namespace prefix to namespace uri, before you can use the prefix in your xpath. In this case, use XmlNamespaceManager to define the mapping, then you can simply pass the namespace manager instance as 2nd parameter of SelectNodes() :

    ......
    var nsManager = new XmlNamespaceManager(new NameTable());
    //register mapping of prefix to namespace uri 
    nsManager.AddNamespace("gml", "http://www.opengis.net/gml");
    //pass the namespace manager instance as 2nd param of SelectNodes():
    XmlNodeList xnList = xml.SelectNodes("HostipLookupResultSet/gml:featureMember/Hostip", nsManager);
    ......
    

    There is another problem in your xpath. gml:featureMember is not the root element of the XML, it is the root's child. So you need to mention the root element before gml:featureMember as demonstrated above, or alternatively using descendant-or-self axis like : //gml:featureMember/Hostip (the latter would be a bit slower though).