Reading XML file results in index out of range exception - c#

Using C# I have an XML file like
<?xml version="1.0" encoding="utf-8"?>
<root>
<Account>
<name>Jani</name>
</Account>
</root>
and I also have a function to read the name node as:
XmlDocument xmlDoc = new XmlDocument();
xmlDoc.Load("lib//user.xml");
XmlNode node;
node = xmlDoc.DocumentElement;
string name = node.Attributes[0].Value;
label1.Text = name.ToString();
but I am getting index out of range error as:
Why is this happening?

node = xmlDoc.DocumentElement;
string name = node.Attributes[0].Value;
node is your root node. Which looks like this:
<root>
How many attributes does it have? None, as it turns out. An attribute in XML is one of these bar="baz" things:
<foo bar="baz">
node.Attributes[0] refers to the first attribute. There is no first attribute, there's no second attribute -- you didn't use attributes in this XML at all. Hence, that's out of range. There's no first item in an empty collection.
What you want is an element named name, which is farther down inside your XML tree.
Probably this:
var node = xmlDoc.DocumentElement.SelectSingleNode("/root/Account/name");
And then you'll want to look at node.InnerText to get "Jani" out of it.

You are trying to read node.Attributes[0].Value but there is no attribtues in your sample XML file. Not sure of the exact syntax but it should probably be closer to node.Value

As mentioned by other answers, your current XML does not have attributes.
private void DoIt()
{
XmlDocument xmlDoc = new XmlDocument();
xmlDoc.Load(#"M:\StackOverflowQuestionsAndAnswers\38924171\38924171\data.xml");
XmlNode node;
node = xmlDoc.DocumentElement;
//string name = node.Attributes[0].Value;
string name = node["Account"].InnerText;
}
If your XML did have attributes
<?xml version="1.0" encoding="utf-8"?>
<root>
<Account name="Jani" />
</root>
Then you could do this:
private void DoItAgain()
{
XmlDocument xmlDoc = new XmlDocument();
xmlDoc.Load(#"M:\StackOverflowQuestionsAndAnswers\38924171\38924171\data2.xml");
XmlNode node;
node = xmlDoc.DocumentElement;
string name = node["Account"].Attributes[0].Value;
}

Related

Getting nsi:type in xml

So I have a XML File that looks like this
<MyObjectBuilder_Sector xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<SectorObjects>
<MyObjectBuilder_EntityBase xsi:type="MyObjectBuilder_CubeGrid">
<EntityId>-8358349049537298307</EntityId>
<LinearVelocity x="0" y="0" z="0" />
</MyObjectBuilder>
</SectorObjects>
</MyObjectBuilder_Sector>
I was curious how in C# how I could retrieve that MyObjectBuilder_CubeGrid from the MyObjectBuilder_EntityBase node. The best i got is this
fileLoc = ofd.FileName;
XmlDocument xdoc = new XmlDocument();
xdoc.Load(fileLoc);
XmlNode typeOfNode = xdoc.SelectSingleNode("MyObjectBuilder_Sector/SectorObjects/MyObjectBuilder_EntityBase").ToString();
Which of course just gets me the node not the xsi:type of the node. I've looked all over for it and can not find an answer.
-Cheers
     Jacob Bender
You can access node's attribute this way :
XmlNode typeOfNode =
xdoc.SelectSingleNode("MyObjectBuilder_Sector/SectorObjects/MyObjectBuilder_EntityBase");
//here typeValue variable will contains "MyObjectBuilder_CubeGrid"
String typeValue = typeOfNode.Attributes["xsi:type"].Value;

XML select single node not returning anything

I have the following method that is supposed to return a string that holds the calories for a given food item in an xml menu.
public string calorieCount(int choice)
{
string calCount = "250";
XmlDocument doc = new XmlDocument();
doc.Load(path);
XmlElement root = doc.DocumentElement;
XmlNode node = doc.SelectSingleNode("/menu/item[#name='Burger']/calories");
string checker = node.Value;
MessageBox.Show(checker);//returning nothing
return checker;
}
And my XML file looks like this:
<?xml version="1.0" encoding="utf-8" ?>
<menu>
<!-- Burger -->
<item name="Burger">
<name>Burger</name>
<price>$5.99</price>
<calories>500</calories>
<description>A burger made with 100% angus beef and grilled to your liking. Served with fries</description>
<count>25</count>
</item>
Why is it returning an empty string? Is my call to SelectSingleNode incorrect?
Thank you in advance.
Use InnerText instead of Value
Replace
string checker = node.Value;
With
string checker = node.InnerText;

C# how to create a custom xml document

I'm really just trying to create a custom xml document for simple configuration processing.
XmlDocument xDoc = new XmlDocument();
string[] NodeArray = { "Fruits|Fruit", "Vegetables|Veggie"};
foreach (string node in NodeArray)
{
XmlNode xmlNode = xDoc.CreateNode(XmlNodeType.Element,node.Split('|')[0],null);
//xmlNode.Value = node.Split('|')[0];
xmlNode.InnerText = node.Split('|')[1];
xDoc.DocumentElement.AppendChild(xmlNode);
}
What i'm trying to get is this.
<?xml version="1.0" encoding="ISO-8859-1"?>
<Fruits>Fruit</Fruits>
<Vegetables>Veggie</Vegetables>
i get not set to value of an object at xDoc.DocumentElement.AppendChild(xmlNode);
Unfortunately, You can't make that XML structure.
All XML documents must have a single root node. You can't have more.
Try something like this
XmlDocument xDoc = new XmlDocument();
xDoc.AppendChild( xDoc.CreateElement("root"));
string[] NodeArray = { "Fruits|Fruit", "Vegetables|Veggie" };
foreach (string node in NodeArray)
{
XmlNode xmlNode = xDoc.CreateNode(XmlNodeType.Element, node.Split('|')[0], null);
//xmlNode.Value = node.Split('|')[0];
xmlNode.InnerText = node.Split('|')[1];
xDoc.DocumentElement.AppendChild(xmlNode);
}
It is not possible to have that XML structure as XML MUST have a single root element. You may want to try:
<?xml version="1.0" encoding="ISO-8859-1"?>
<items>
<Fruits>Fruit</Fruits>
<Vegetables>Veggie</Vegetables>
</items>

How to read single node value from xml file

Hi i am trying to get value from xml but it shows node null.
Here is my xml file.
<?xml version="1.0" encoding="utf-8"?>
<result xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="https://www.cfhdocmail.com/TestAPI2/Result.xsd https://www.cfhdocmail.com/TestAPI2/Result.xsd" xmlns="https://www.cfhdocmail.com/TestAPI2/Result.xsd">
<data>
<key>MailingGUID</key>
<value>0aa2b2e3-7afa-4002-ab2f-9eb4cbe33ae7</value>
</data>
<data>
<key>OrderRef</key>
<value>52186</value>
</data>
</result>
I want to get "MailingGUID" value.
Here is the code that i have tried:
private void readXML()
{
XmlDocument xml = new XmlDocument();
// You'll need to put the correct path to your xml file here
xml.Load(Server.MapPath("~/XmlFile11.xml"));
// Select a specific node
XmlNode node = xml.SelectSingleNode("result/data/value");
// Get its value
string name = node.InnerText;
}
Please tell me how i can get MailingGUID value.
Thanks
UPDATE:
I think there might be something wrong with your schemas, I removed references to them and your code worked fine. I tried this:
const string str = "<?xml version=\"1.0\" encoding=\"utf-8\"?><result><data><key>MailingGUID</key><value>0aa2b2e3-7afa-4002-ab2f-9eb4cbe33ae7</value></data><data><key>OrderRef</key><value>52186</value></data></result>";
var xml = new XmlDocument();
xml.LoadXml(str);
xml.DocumentElement.SelectSingleNode("/result/data/value").InnerText
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
DocumentBuilder builder = factory.newDocumentBuilder();
//Parsing of xml is done here
Document doc = builder.parse(new File("C:\\Users\\User_Name\\Documents\\My Received Files\\PDSL_ABM.xml"));
//Here we get the root element of XML and print out
doc.getDocumentElement().normalize();
System.out.println ("Root element of the doc is " + doc.getDocumentElement().getNodeName());
NodeList list = doc.getElementsByTagName("MailingGUID");
int totalMailingGUID =list.getLength();
System.out.println("Total no of MailingGUID : " + totalSupplierPartID);
//Traversing all the elements from the list and printing out its data
for (int i = 0; i < list.getLength(); i++) {
//Getting one node from the list.
Node childNode = list.item(i);
System.out.println("MailingGUID : " + childNode.getTextContent());
}

Problem in reading XML node with unknown root/parent nodes

I have been trying to read an xml file. I have to extract value of nodes "Date" and "Name", but the problem is, they might appear at any level in XML hierarchy.
So when I try with this code,
XmlDocument doc = new XmlDocument();
doc.Load("test1.xml");
XmlElement root = doc.DocumentElement;
XmlNodeList nodes = root.SelectNodes("//*");
string date;
string name;
foreach (XmlNode node in nodes)
{
date = node["date"].InnerText;
name = node["name"].InnerText;
}
and the XML file is ::
<?xml version="1.0" encoding="utf-8"?>
<root>
<child>
<name>Aravind</name>
<date>12/03/2000</date>
</child>
</root>
the above code errors out, as <name> and <date> are not immediate child Elements of root.
is it possible to assume that parent/root nodes are unknown and just with the name of the nodes, copy the values ??
Depending on the exception you are getting, this may or may not be the exact solution. However, I would definitely check that date and name exist before doing a .InnerText on them.
foreach (XmlNode node in nodes)
{
dateNode = node["date"];
if(dateNode != null)
date = dateNode.InnerText;
// etc.
}
I would read up on XPATH and XPATH for C# to do this more efficiently
http://support.microsoft.com/kb/308333
http://www.w3schools.com/XPath/xpath_syntax.asp
Here's a little method that should allow you to get the innerText easily.
function string GetElementText(string xml, string node)
{
XPathDocument doc = new XPathDocument(xml);
XPathNavigator nav = doc.CreateNavigator();
XPathExpression expr = nav.Compile("//" + node);
XPathNodeIterator iterator = nav.Select(expr);
while (iterator.MoveNext())
{
// return 1st but there could be more
return iterator.Current.Value;
}
}
Try to use LINQ:
string xml = #"<?xml version='1.0' encoding='utf-8'?>
<root>
<date>12/03/2001</date>
<child>
<name>Aravind</name>
<date>12/03/2000</date>
</child>
<name>AS-CII</name>
</root>";
XDocument doc = XDocument.Parse(xml);
foreach (var date in doc.Descendants("date"))
{
Console.WriteLine(date.Value);
}
foreach (var date in doc.Descendants("name"))
{
Console.WriteLine(date.Value);
}
Console.ReadLine();
The Descendants method allows you to get all the elements that have a specified name.

Categories