xRalf
asked on
No elements when reading XML
Hi,
I'm reading XML file of the following structure.
<?xml version="1.0" encoding="utf-8"?>
<PriceList version="1.0" application="some text" note="some text" xmlns="http://...xsdfile.xsd">
<Products>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
</Products>
</Pricelist>
with this code snippet.
foreach (XmlNode pictureNode in doc.DocumentElement.Select Nodes("Pro ductItem") )
{
// processing
}
The problem is that doc.DocumentElement.Select Nodes("Pro ductItem") selects no elements.
When I change the XML structure to
<?xml version="1.0" encoding="utf-8"?>
<Products>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
</Products>
everything is OK. Where is the mistake?
thanks
I'm reading XML file of the following structure.
<?xml version="1.0" encoding="utf-8"?>
<PriceList version="1.0" application="some text" note="some text" xmlns="http://...xsdfile.xsd">
<Products>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
</Products>
</Pricelist>
with this code snippet.
foreach (XmlNode pictureNode in doc.DocumentElement.Select
{
// processing
}
The problem is that doc.DocumentElement.Select
When I change the XML structure to
<?xml version="1.0" encoding="utf-8"?>
<Products>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
</Products>
everything is OK. Where is the mistake?
thanks
try
foreach (XmlNode pictureNode in doc.DocumentElement.Select Nodes("Pro ducts"))
{
pictureNode.innerXML...
}
do a foreach for the inner node to get the value...
foreach (XmlNode pictureNode in doc.DocumentElement.Select
{
pictureNode.innerXML...
}
do a foreach for the inner node to get the value...
I will change the loop like this
foreach (XmlNode pictureNode in doc.DocumentElement.Select Nodes("//P roducts/Pr oductItem" ))
{
// processing
}
foreach (XmlNode pictureNode in doc.DocumentElement.Select
{
// processing
}
You can also use "//Products". The expression is saying in all nodes, return all nodes with tagname of 'products'. If you leave out the '//', then you are saying, in the current node return all of the nodes with tagname of 'products'.
ASKER
Thanks,
but none of the solutions works. There are approximately 10000 items of ProductItem but the for cycle executes 0 times. It works only when I delete PriceList tags from XML file.
The code
XmlNode node = doc.DocumentElement.Select SingleNode ("PriceLis t") doesn't work either.
node will be null after this statement.
but none of the solutions works. There are approximately 10000 items of ProductItem but the for cycle executes 0 times. It works only when I delete PriceList tags from XML file.
The code
XmlNode node = doc.DocumentElement.Select
node will be null after this statement.
ASKER
When I delete the attributes of XML as follows it didn't help either. What is bad with this XML?
<?xml version="1.0" encoding="utf-8"?>
<PriceList>
<Products>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
</Products>
</Pricelist>
<?xml version="1.0" encoding="utf-8"?>
<PriceList>
<Products>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
</Products>
</Pricelist>
I found the problem. The XML you are using has a default name space. The xmlns="http://...xsdfile.xsd" sets the PriceList node and all of its children to that default namespace. The XPath you are specifying does not contain the namespace reference so it is searching for nodes that are not members of the namespace.
The following fixes your code by specifying through the NameSpaceManager what namespace to use
The following fixes your code by specifying through the NameSpaceManager what namespace to use
string XmlStr = @"<?xml version='1.0' encoding='utf-8'?>
<PriceList version='1.0' application='some text' note='some text' xmlns='http://...xsdfile.xsd'>
<Products>
<ProductItem>One</ProductItem>
<ProductItem>Two</ProductItem>
<ProductItem>Three</ProductItem>
</Products>
</PriceList>";
XmlDocument doc = new XmlDocument();
doc.LoadXml(XmlStr);
XmlNamespaceManager nsmgr = new XmlNamespaceManager(doc.NameTable);
nsmgr.AddNamespace("default", "http://...xsdfile.xsd"); //Create reference to the default namespace
XmlNodeList nodeList = doc.SelectNodes("//default:ProductItem", nsmgr); //Reference the ProductItem node in the default namespace
if (nodeList.Count == 0)
System.Console.WriteLine("No items found");
foreach (XmlNode pictureNode in nodeList)
{
System.Console.WriteLine(pictureNode.InnerText);
}
ASKER
Hi MogalManic,
but here is no namespace
<?xml version="1.0" encoding="utf-8"?>
<PriceList>
<Products>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
</Products>
</Pricelist>
but here is no namespace
<?xml version="1.0" encoding="utf-8"?>
<PriceList>
<Products>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
<ProductItem>
</ProductItem>
</Products>
</Pricelist>
When there is no namespace, you do NOT specify the namespace in the xpath. So the xpath is just "//ProductItem" (the // is still important)
try this one - i think i missed the price list node in my reference to the productimte
XmlNodeList = doc.DocumentElement.Select Nodes("//P riceList/P roducts/Pr oductItem" );
for (XmlNode node in XmlNodeList)
{
// node is now the product item node here....
}
the above code should work
XmlNodeList = doc.DocumentElement.Select
for (XmlNode node in XmlNodeList)
{
// node is now the product item node here....
}
the above code should work
ASKER
Hi,
I tried the code from every comment but only code from MogalManic is working. I rewritten it as follows (in codesnippet).
nodeList contains the nodes I was looking for, but when I uncomment the inner foreach loop, it doesn't find nothing. Is there some mistake?
Other interesting thing is that when I delete from XML "version='1.0' application='some text' note='some text' xmlns='http://...xsdfile.xsd'" it doesn't find anything. How are namespaces working? I know nothing about them.
thanks
I tried the code from every comment but only code from MogalManic is working. I rewritten it as follows (in codesnippet).
nodeList contains the nodes I was looking for, but when I uncomment the inner foreach loop, it doesn't find nothing. Is there some mistake?
Other interesting thing is that when I delete from XML "version='1.0' application='some text' note='some text' xmlns='http://...xsdfile.xsd'" it doesn't find anything. How are namespaces working? I know nothing about them.
thanks
XmlDocument doc = new XmlDocument();
doc.Load(@"D:\pricelist.xml");
XmlNamespaceManager nsmgr = new XmlNamespaceManager(doc.NameTable);
nsmgr.AddNamespace("default", "http://www....xsd"); //Create reference to the default namespace
XmlNodeList nodeList = doc.SelectNodes("//default:ProductItem", nsmgr); //Reference the ProductItem node in the default namespace
foreach (XmlNode pictureNode in nodeList)
{
MessageBox.Show(pictureNode.InnerText);
//foreach (XmlNode pctNode in pictureNode.SelectNodes("//default:ProductPictures/ProductPictureItem/ProductPictureDetail", nsmgr))
//{
// MessageBox.Show(pctNode.InnerText);
//}
}
ASKER CERTIFIED SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
The problem is that you are not observing the hierarchy of your document structure. In the first situation the is the documentElement but the first level below that is not the elements. So you need to use:
doc.DocumentElement.Select
To get all the elements contained with the element.
Regards,
TimCottee