Get data from xml - c#

I want get <SNILS> node:
<ArrayOfEmployee xmlns=""
xmlns:i="http://www.w3.org/2001/XMLSchema-instance" version="2.0.11"
formatVersion="2.0" system="ARM">
<Employee>
<AdditionalLaborAgreement i:nil="true" /> <CertificateEducationList>
<Document> <SNILS>1111111111111</SNILS>
</Document>
</CertificateEducationList>
</Employee>
Code:
XmlNodeList nodes = xml.GetElementsByTagName("Employee");
XmlNode node = xml.SelectSingleNode("SVED_PR_GS/ZGLV/FILENAME");
int Count = 2;
foreach (XmlNode n in nodes)
{
XmlNode smr_vsi = n.SelectSingleNode("SNILS");
Console.WriteLine(n.SelectSingleNode(smr_vsi.InnerText));
}
Error: Console.WriteLine(n.SelectSingleNode(smr_vsi.InnerText));
The object reference does not point to an instance of the object.

Your XML is malformed. Its missing </ArrayOfEmployee> element.
You can get the desired node in one of the 2 ways:
// Provide full XPath
XmlNode smr_vsi = n.SelectSingleNode("CertificateEducationList/Document/SNILS");
//Provide find on any path hint.
XmlNode smr_vsi = n.SelectSingleNode("//SNILS");
But, do check for null before using it:
if(smr_vsi != null)
Console.WriteLine(smr_vsi.InnerText);

Related

C# XmlDocument how to get pointer to root element and iterate over children

In XML Document:
Foo.xml
<products>
<product>
<id>1</id>
<name>Foo</name>
</product>
<product>
<id>2</id>
<name>Bar</name>
</product>
</products>
How to get this root element, iterate over his child elements and get their properties?
Bar.cs
XmlDocument doc = new XmlDocument();
doc.Load(path + "/foo.xml");
XmlNode mainNode = doc.DocumentElement.SelectSingleNode("products");
XmlNode root = mainNode.FirstChild; //null
foreach (XmlNode node in mainNode)
{
int id = Convert.ToInt32(node["id"].InnerText);
string name = node["name"].InnerText);
list.Items.Add(id);
list.Items.Add(name);
}
This code implicates that mainNode is null. What is the best practise of doing that?
The DocumentElement is the outermost element of the XML, i.e. the <products> element. You can't select another <products> element below it.
What you can do:
XmlNode mainNode = doc.SelectSingleNode("products");
or
XmlNode mainNode = doc.DocumentElement;
or
XmlNode mainNode = doc.DocumentElement.SelectSingleNode("//products");
The second one is probably the fastest, since it does not need to parse and process a query. The last one is overkill and should be avoided for clean code reasons (KISS principle).

C# XML to dropdownBox

Returned XML from URL:
<root>
<APIVersion>0.1</APIVersion>
<resource>persons</resource>
<search>givenname</search>
<query>andreas</query>
<limit>400</limit>
<results>
<item>
<persons>
<personId>21168</personId>
<givenName>Andreas</givenName>
<familyName>Garpe</familyName>
<email>andreas.garpe#t-fk.no</email>
<mobilePhone/>
<workPhone/>
<positions>...</positions>
</persons>
</item>
<item>...</item>
<item>...</item>
<item>...</item>
</results>
</root>
(Keep in mind that "item" is the objects with personnel info.)
I have a textbox defined as bunifuTextbox1.
I input a name, and it returns the names from the returned XML result and put all the names returned into a dropdown box.
private void button1_Click(object sender, EventArgs e)
{
string address = "http://ws.t-fk.no/?resource=persons&search=givenname&string=" + bunifuTextbox1.text;
XmlDocument doc1 = new XmlDocument();
doc1.Load(address);
XmlElement root = doc1.DocumentElement;
XmlNodeList nodes = root.SelectNodes("/results/item");
foreach (XmlNode node in nodes)
{
string tempf = node["persons"]["givenName"].InnerText;
bunifuDropdown1.AddItem(tempf);
}
}
I'm not sure why this doesen't work. Any help?
Your XPath is incorrect.
Instead of
XmlNodeList nodes = root.SelectNodes("/results/item");
try
XmlNodeList nodes = root.SelectNodes("results/item");
or
XmlNodeList nodes = root.SelectNodes("./results/item");
or
XmlNodeList nodes = root.SelectNodes("//results/item");
Use "results/item" or "./results/item" for an item element that is a child of a results element that is a child of the root node.
Using "//results/item" will select item elements that are children of results elements where the results element is anywhere in the XML.

Get childNode in childNode in XMLDocument

I have XML response from service and I need to get value of tag that exist in child node that this child node is a child node.
For example: This is an example of xml.
<ashrait>
<response>
<command>inquire</command>
<inquire>
<row>
<ResponseCode>000</ResponseCode>
<ResponseText>
Permitted.
</ResponseText>
<ResponseXML>
<ashrait>
<response>
<message>Permitted .</message>
<userMessage>Permitted .</userMessage>
</response>
</ashrait>
</ResponseXML>
</row>
</inquire>
</response>
</ashrait>
I need the the value in tag "userMessage" that exists in tag "ResponseXML".
I know that to get the node of "ResponseXML" I need for those lines:
var doc = new XmlDocument();
doc.LoadXml(responseFile);
ChildNode result = doc.GetElementsByTagName("ResponseXML")[0];
But how i get the tag userMessage in childNode "ResponseXML"?
Thanks
UPDATE:
I figured out how to do it.
Search for all the children with the tag and choose the order they want.
Create a model for your XML, load that model using XmlSerializer.
Check this Microsoft Docs.
https://learn.microsoft.com/en-us/dotnet/standard/serialization/examples-of-xml-serialization
Use
SelectNodes method: https://msdn.microsoft.com/en-us/library/hcebdtae(v=vs.110).aspx
or SelectSingleNode method: https://msdn.microsoft.com/en-us/library/system.xml.xmlnode.selectsinglenode(v=vs.110).aspx
var doc = new XmlDocument();
doc.LoadXml(Xml);
XmlNode xn = doc.SelectSingleNode("//ashrait//inquire//row//ResponseXML//message");
var innerText = xn.InnerText;

read child nodes xml

Here is my xml which i am trying to read.
<VacancyList xmlns="urn:abc" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" generated="2016-04-20T11:42:47" xsi:schemaLocation="http://www.abc.in/dtd/vacancy-list.xsd">
<Vacancy id="1619993" date_start="2016-04-15" date_end="2016-04-22" reference_number="">
<Versions>
<Version language="nb">
<Title>Marketing Specialist</Title>
<TitleHeading/>
<Location>CXCXC</Location>
<Engagement/>
<DailyHours/>
<Region>
<County id="11">sds</County>
<County id="1">zxzx</County>
</Country>
</Region>
<Categories>
<Item type="position-type" id="3909">sER</Item>
<Item type="duration" id="contract">ss</Item>
<Item type="extent" id="fulltime">sd</Item>
<Item type="operating-time" id="day">s</Item>
</Categories>
</Version>
</Versions>
</Vacancy>
</VacancyList>
I want to read node location so wrote below code
XmlDocument xd = new XmlDocument();
xd.Load("https://abc.in/list.xml");
XmlNamespaceManager ns = new XmlNamespaceManager(xd.NameTable);
ns.AddNamespace("msbld", "urn:abc");
XmlNodeList nodelist = xd.SelectNodes("//msbld:VacancyList", ns);
if (nodelist != null)
foreach (XmlNode node in nodelist)
{
XmlNode nodelist1 = node.SelectSingleNode("Vacancy");
if (nodelist1 != null)
foreach (XmlNode node1 in nodelist1)
{
var k = node1.Attributes.GetNamedItem("Location").Value;
}
}
But i dont get anything in variable "node1". How to fix this?
Also is there any better solution for this?
Update1
i modified code but i only get node Title. cant get others inside Version node like Location.
if (nodelist != null)
foreach (XmlNode node in nodelist)
{
XmlNode nodelist1 = node.SelectSingleNode("//msbld:Vacancy/msbld:Versions",ns);
if (nodelist1 != null) {
XmlNode nodelist2 = nodelist1.SelectSingleNode("//msbld:Version", ns);
foreach (XmlNode node3Node in nodelist2)
{
var k = node3Node.Attributes.GetNamedItem("Location").Value;
}
}
}
xmlns="urn:abc" is a default namespace. Notice that descendant elements without prefix inherits ancestor's default namespace implicitly. You need to use the same prefix that references default namespace URI for acessing Vacancy and Location as well :
XmlNode nodelist1 = node.SelectSingleNode("msbld:Vacancy", ns);
Your updated code introduces an entirely different problem; / at the beginning of a path expression will always reference document element, unless you explicitly set the context to current active context by using . before /, for example :
XmlNode nodelist1 = node.SelectSingleNode(".//msbld:Vacancy/msbld:Versions",ns);
If you only need the Location element then you can do it like this:
var doc = XElement.Load("path/to/file");
var location = doc.Descendants
.FirstOrDefault(e => e.Name.LocalName == "Location"));

How to get the value for multiple subnode in xml?

Xml code:
<Report>
<ChartData>
<ListName>area</ListName>
<ViewName>Selecte List</ViewName>
<YAxisFields>
<YAxisField>
<Name>Scheduled Start Date/Time</Name>
<DataType>DateTime</DataType>
<Category>Year</Category>
</YAxisField>
</YAxisFields>
<XAxisFields>
<XAxisField>
<Name>Release Type</Name>
<DataType>String</DataType>
<Category>
</Category>
</XAxisField>
</XAxisFields>
</ChartConfig>
</Report>
I got the value for the subnode listname and viewname by using the
below code,
XmlDocument doc = new XmlDocument();
doc.Load("XmlFileName");
XmlNodeList node = doc.SelectNodes("Report/ChartData");
foreach (XmlNode xn in node)
{ xn["ListName"].InnerXml = chartname;
xn["ViewName"].InnerXml = SelectedList;
**xn["YAxisFields/YAxisField"].InnerXml = yaxisfield; //not working, need to get the value for this xml node,need help in this line dono how to proceed**
doc.Save("XmlFilename");
}
First i have tried with code like this instead of above code,in this
i need to create number of objects in order get the value for each
node so i tried by creating object for xmlnodelist then i used
foreach loop to get the value for each node but in this couldnt get
the value for YAxisFields/YAxisField because it also has parent node
as YAxisFields and subnode as YAxisField so there is only way to
create number of objects for xmlnode or is there any other way to do
this?
XmlDocument doc = new XmlDocument();
doc.Load("XmlFileName");
XmlNode Listnode = doc.SelectSingleNode("Report/ChartData/ListName");
XmlNode Viewnode = doc.SelectSingleNode("Report/ChartData/ViewName");
if (Listnode != null)
{
Listnode.InnerXml = chartname;
Viewnode.InnerXml = SelectedList; ;
doc.Save("XmlFileName");
Use Linq to XML XDocument, like this:
doc.Root.Descendants("ChartData").ToList().ForEach(node =>
{
node.Element("ListName").Value = chartname;
node.Element("ViewName").Value = SelectedList;
});

Categories

Resources