Need help to deserialize XML data - c#

I am trying to deserialize the below XML using C#
<?xml version="1.0" encoding="utf-8"?>
<Invoice>
<Samples>
<Sample>
<AccountId>1e547ae6-9a6d-d18f-958b-22000b83a845</AccountId>
<AccountNumber>55761598808</AccountNumber>
</Sample>
<Sample>
<AccountId>1e547ae6-9a6d-d18f-958b-22000b83a845</AccountId>
<AccountNumber>55761598808</AccountNumber>
</Sample>
</Samples>
</Invoice>
Here are the classes that I have defined to deserialize
[DataContract(Name = "Sample")]
public class Sample
{
[DataMember(Name = "AccountId")]
public string AccountId { get; set; }
[DataMember(Name = "AccountNumber")]
public string AccountNumber { get; set; }
}
[DataContract(Name = "Samples")]
public class Samples
{
[DataMember(Name = "Sample")]
public List<Sample> Sample { get; set; }
}
[DataContract(Name = "Invoice")]
public class Invoice
{
[DataMember(Name = "Samples")]
public Samples Samples { get; set; }
}
The corresponding test case to deserialize is as follows
public void SampleXmlTest()
{
dynamic env = SUT.GetEnvironment();
string dbConnStrUrjanet = (string)env.AvidUtility.UrjanetDB;
XmlSerializer deserializer = new XmlSerializer(typeof(CommonAvidXmlDto.Invoice));
TextReader reader = new StreamReader(#"C:\Users\SJuluru\Desktop\Sample XML\Samplexml.xml");
Object obj = deserializer.Deserialize(reader);
CommonAvidXmlDto.Invoice XmlData4 = (CommonAvidXmlDto.Invoice)obj;
After running the test case debug mode, XmlData4 has null without having the XML data. Kindly help me how to modify this code to work.

DataContract and DataMember are attribute of DataContractSerializer so you shoud replace your serializer msdn or use XmlSerializer's attributes (XmlRoot, XmlElement etc)

Change deserialize classes:
using System;
using System.Xml.Serialization;
using System.Collections.Generic;
namespace ConsoleApp4
{
[XmlRoot(ElementName = "Sample")]
public class Sample
{
[XmlElement(ElementName = "AccountId")]
public string AccountId { get; set; }
[XmlElement(ElementName = "AccountNumber")]
public string AccountNumber { get; set; }
}
[XmlRoot(ElementName = "Samples")]
public class Samples
{
[XmlElement(ElementName = "Sample")]
public List<Sample> Sample { get; set; }
}
[XmlRoot(ElementName = "Invoice")]
public class Invoice
{
[XmlElement(ElementName = "Samples")]
public Samples Samples { get; set; }
}
}
Use below method for deserialize:
private static Invoice LoadInvoice(string fileName)
{
var serializer = new XmlSerializer(typeof(Invoice));
if (!File.Exists(fileName))
{
return null;
}
using (var fs = new FileStream(fileName, FileMode.Open, FileAccess.Read, FileShare.ReadWrite))
{
return (Invoice)serializer.Deserialize(fs);
}
}
Result:

Related

There is an error in XML document (2, 2) when desearlizing xml to c# object

XML
<?xml version="1.0" encoding="UTF-8"?>
<orgc:Organizations xmlns:orgc="urn:workday.com/connector/orgs" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<orgc:Organization>
<orgc:Organization_ID>SR1Code34</orgc:Organization_ID>
<orgc:Organization_Code>SR1Code34</orgc:Organization_Code>
<orgc:Organization_Type>Cost_Center_Hierarchy</orgc:Organization_Type>
<orgc:Organization_Name>LTL Services</orgc:Organization_Name>
<orgc:Organization_Description>LTL Services</orgc:Organization_Description>
<orgc:Organization_Subtype>ORGANIZATION_SUBTYPE-3-20</orgc:Organization_Subtype>
<orgc:Inactive>false</orgc:Inactive>
<orgc:Superior_Organization>DL2Code11</orgc:Superior_Organization>
</orgc:Organization>
<orgc:Organization>
<orgc:Organization_ID>SR1Code35</orgc:Organization_ID>
<orgc:Organization_Code>SR1Code35</orgc:Organization_Code>
<orgc:Organization_Type>Cost_Center_Hierarchy</orgc:Organization_Type>
<orgc:Organization_Name>Consolidation</orgc:Organization_Name>
<orgc:Organization_Description>Consolidation</orgc:Organization_Description>
<orgc:Organization_Subtype>ORGANIZATION_SUBTYPE-3-20</orgc:Organization_Subtype>
<orgc:Inactive>false</orgc:Inactive>
<orgc:Superior_Organization>DL2Code11</orgc:Superior_Organization>
</orgc:Organization>
</orgc:Organizations>
Class
[XmlRoot(ElementName = "Organizations", Namespace = "urn: workday.com/connector/orgs", IsNullable = true )]
public class CostCenterHierarchy
{
[XmlElement("orgc:Organization_ID")]
public string CostCenterHierarchyId { get; set; }
[XmlElement("orgc:Organization_Code")]
public string Code { get; set; }
[XmlElement("orgc:Organization_Name")]
public string Name { get; set; }
[XmlElement("orgc:Organization_Description")]
public string Description { get; set; }
[XmlElement("orgc:Organization_Subtype")]
public string Subtype { get; set; }
[XmlElement("orgc:Superior_Organization")]
public string ParentHierarchyId { get; set; }
}
Method to deseralize xml to c# class
private List<CostCenterHierarchy> ProcessCostCenterHierarchy(string filePath)
{
var costCenterHierarchyList = new List<CostCenterHierarchy>();
//var costCenterHierarchy = new CostCenterHierarchy();
XmlSerializer xmlSerializer = new XmlSerializer(typeof(List<CostCenterHierarchy>));
using (var reader = XmlReader.Create(filePath))
{
var test = xmlSerializer.Deserialize(reader);
}
return costCenterHierarchyList;
}
Error Message
Message = "There is an error in XML document (2, 2)."
InnerException = {"<Organizations xmlns='urn:workday.com/connector/orgs'> was not expected."}
I'm not sure where I am going wrong. Seems like it should be pretty easy but I've played around with this and keep getting the same error message. Any help would be much appreciated.
The code below works. You have an array and serialization doesn't like a list as the type. The Url "urn:workday.com/connector/orgs" the serializaer doesn't like and had to replace the "urn:" with "http://workday.com/connector/orgs".
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Serialization;
namespace ConsoleApplication1
{
class Program
{
const string FILENAME = #"c:\temp\test.xml";
static void Main(string[] args)
{
XmlReader reader = XmlReader.Create(FILENAME);
XmlSerializer serializer = new XmlSerializer(typeof(Organizations));
Organizations organizations = (Organizations)serializer.Deserialize(reader);
}
}
[XmlRoot(ElementName = "Organizations", Namespace = "http://workday.com/connector/orgs")]
public class Organizations
{
[XmlElement(ElementName = "Organization", Namespace = "http://workday.com/connector/orgs")]
public List<CostCenterHierarchy> organizations { get; set; }
}
public class CostCenterHierarchy
{
[XmlElement("Organization_ID")]
public string CostCenterHierarchyId { get; set; }
[XmlElement("Organization_Code")]
public string Code { get; set; }
[XmlElement("Organization_Name")]
public string Name { get; set; }
[XmlElement("Organization_Description")]
public string Description { get; set; }
[XmlElement("Organization_Subtype")]
public string Subtype { get; set; }
[XmlElement("Superior_Organization")]
public string ParentHierarchyId { get; set; }
}
}

How to de-serialise a list with multiple xsi:type

I'm using the XmlSerializer in System.Xml.Serialization.
I have a list (or two lists really) separated by xsi:type.
<?xml version="1.0" encoding="utf-8"?>
<ButikerOmbud xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<Info>
<Meddelande>blah blah</Meddelande>
</Info>
<ButikOmbud xsi:type="StoreAssortmentViewModel">
<Typ>Butik</Typ><Nr>2515</Nr>
</ButikOmbud>
<ButikOmbud xsi:type="StoreAssortmentViewModel">
<Typ>Butik</Typ><Nr>2516</Nr>
</ButikOmbud>
<ButikOmbud xsi:type="AgentAssortmentViewModel">
<Typ>Ombud</Typ><Nr>011703-91A</Nr>
</ButikOmbud>
<ButikOmbud xsi:type="AgentAssortmentViewModel">
<Typ>Ombud</Typ><Nr>011703-92B</Nr>
</ButikOmbud>
</ButikerOmbud>
I've created some classes that map to this:
[XmlRoot(ElementName = "ButikerOmbud")]
public class ButiksCollection
{
[XmlElement(ElementName = "Info")]
public Info Info { get; set; }
[XmlElement(ElementName = "ButikOmbud")]
public List<Butik> Butiker { get; set; }
}
[XmlRoot(ElementName = "ButikOmbud")]
[XmlType(TypeName = "StoreAssortmentViewModel")]
public class Butik
{
[XmlElement(ElementName = "Typ")]
public string Typ { get; set; }
[XmlElement(ElementName = "Nr")]
public int Nr { get; set; }
}
and then I'll do this
(ButiksCollection)(new XmlSerializer(typeof(ButiksCollection)).Deserialize(memoryStream));
This should work if only the StoreAssortmentViewModel existed. But given that there exists AgentAssortmentViewModel under the same node. I'm not sure how I should de-serialise this. I'm assuming there should be another collection List<Butik> Agents on ButiksCollection.
The only attribute I've found that seems to map to xsi:type is applied to classes, which I don't think is what I want here
How do I arrange and attribute my classes so this will de-serialize?
Here's all that on dotnetfiddle: https://dotnetfiddle.net/vmT4SK
Try following :
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Xml;
using System.Xml.Serialization;
namespace ConsoleApplication1
{
class Program
{
const string FILENAME = #"c:\temp\test.xml";
static void Main(string[] args)
{
XmlReader reader = XmlReader.Create(FILENAME);
XmlSerializer serializer = new XmlSerializer(typeof(ButiksCollection));
ButiksCollection butik = (ButiksCollection)serializer.Deserialize(reader);
List<StoreAssortmentViewModel> storeAssortments = butik.Butiker.Where(x => x.GetType() == typeof(StoreAssortmentViewModel)).Select(x => (StoreAssortmentViewModel)x).ToList();
List<AgentAssortmentViewModel> agentAssortments = butik.Butiker.Where(x => x.GetType() == typeof(AgentAssortmentViewModel)).Select(x => (AgentAssortmentViewModel)x).ToList();
}
}
[XmlRoot(ElementName = "ButikerOmbud")]
public class ButiksCollection
{
[XmlElement(ElementName = "Info")]
public Info Info { get; set; }
[XmlElement(ElementName = "ButikOmbud")]
public List<Butik> Butiker { get; set; }
}
[XmlRoot(ElementName = "ButikOmbud")]
[XmlInclude(typeof(StoreAssortmentViewModel))]
[XmlInclude(typeof(AgentAssortmentViewModel))]
public class Butik
{
[XmlElement(ElementName = "Typ")]
public string Typ { get; set; }
[XmlElement(ElementName = "Nr")]
public string Nr { get; set; }
}
public class Info
{
public string Meddelande { get; set; }
}
public class StoreAssortmentViewModel : Butik
{
}
public class AgentAssortmentViewModel : Butik
{
}
}

Unable to get values from XML using xPath C#

I have two XML files, I am able to get data through xPath in c# from first XML which here:
<CONSOLIDATED_LIST xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="https://www.example/acb.xsd"
dateGenerated="2018-04-19T19:18:41.129-04:00">
<INDIVIDUALS>
<INDIVIDUAL>
<DATAID>2975591</DATAID>
<VERSIONNUM>1</VERSIONNUM>
<FIRST_NAME>ABC</FIRST_NAME>
<SECOND_NAME>XYZ</SECOND_NAME>
<INDIVIDUAL_ALIAS>
<QUALITY>Good</QUALITY>
<ALIAS_NAME>abcd</ALIAS_NAME>
</INDIVIDUAL_ALIAS>
<INDIVIDUAL_ALIAS>
<QUALITY>Bad</QUALITY>
<ALIAS_NAME>ylmn</ALIAS_NAME>
</INDIVIDUAL_ALIAS>
</INDIVIDUAL>
</INDIVIDUALS>
</CONSOLIDATED_LIST>
the way I am getting Data, please also see the comments inside code.
var xml = DownloadString(link); //link refers to XML file on web
e = XElement.Parse(xml);
//parentNodeForPerson = "INDIVIDUAL" for above and "sdnEntry" for below;
var lstIndividuals = e.Descendants(parentNodeForPerson);
Data _individualData;
List<Data> individualList = new List<Data>();
foreach (var individual in lstIndividuals)
{
_individualData = new Data();
//personParentValue1 for above is FIRST_NAME and below is firstName
_individualData.First_Name = individual.Descendants(personParentValue1)
.Any() == true ? individual.Descendants(personParentValue1).First().Value : "";
//personParentValue2 for above is SECOND_NAME and below is lastName
_individualData.Last_Name = individual.Descendants(personParentValue2)
.Any() == true ? individual.Descendants(personParentValue2).First().Value : "";
//childNodeForPersonfor above is INDIVIDUAL_ALIAS and below is aka
var lstIndvidualAlias = individual.Descendants(childNodeForPerson);
_individualData.Alias = new List<string>();
foreach (var alias in lstIndvidualAlias)
{
//personChildValue1 for above is ALIAS_NAME and below is lastName & fisrtName
if (!String.IsNullOrWhiteSpace(alias.Descendants(personChildValue1).First().Value))
{
_individualData.Alias.Add(alias.Descendants(personChildValue1)
.Any() == true ? alias.Descendants(personChildValue1).First().Value : "");
}
}
individualList.Add(_individualData);
}
this is XML where I am not getting data
<List xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://tempuri.org/List.xsd">
<publshInformation>
<Publish_Date>04/18/2018</Publish_Date>
<Record_Count>6299</Record_Count>
</publshInformation>
<sdnEntry>
<lastName>ABCD</lastName>
<fisrtName>XYS</fisrtName>
<akaList>
<aka>
<category>strong</category>
<lastName>ABCDT</lastName>
<fisrtName>XYS</fisrtName>
</aka>
<aka>
<category>Weak</category>
<lastName>AssDT</lastName>
<fisrtName>XYsS</fisrtName>
</aka>
</akaList>
</sdnEntry>
</List>
Edit:
Data Class
public class Data
{
public string Last_Name { get; set; }
public string First_Name { get; set; }
public List<string> Alias { get; set; }
}
SOLUTION
Yes, that's normal and depends on namespaces.
Just edit your LINQ queries and go from the one you used:
var lstIndividuals = e.Descendants(parentNodeForPerson);
to this:
var lstIndividuals = e.Descendants().Where(f => f.Name.LocalName.ToString() == parentNodeForPerson);
And it will work.
LONG EXPLANATION
The above solution basically ignores all namespace information when retrieving elements by name.
The things is that in the first XML you have:
<CONSOLIDATED_LIST xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="https://www.example/acb.xsd"
dateGenerated="2018-04-19T19:18:41.129-04:00">
Whilst in the second we find
<List xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://tempuri.org/List.xsd">
The second XML has two namespaces defined, which throws your LINQ queries out of whack; in fact, if you just removed this from the second XML
xmlns="http://tempuri.org/List.xsd"
your code would work without any changes.
To start with, you can read the answers to What does “xmlns” in XML mean?, especially this one. In short, namespaces can be useful e.g. when you combine XMLs from different sources and you get elements with the same name: by prepending a namespace, elements with the same name will be seen as different:
<namespaceA:elementName>blah </namespaceA:elementName>
<namespaceB:elementName>blah blah</namespaceB:elementName>
In your XML you have two namespaces but, when looking for Descendants you don't specify which namespace your elements belong to.
Another solution, perhaps more robust than the quick one above, would be specifying the namespace the name of an element belongs to, e.g. like the OP does in this question, using XName.Get: in your case, you would get the nodes of the second XML this way:
var lstIndividuals = e.Descendants(XName.Get(parentNodeForPerson, "http://tempuri.org/List.xsd"));
which works because the URI specified (http://tempuri.org/List.xsd) is the one of the default namespace you declared:
xmlns="http://tempuri.org/List.xsd"
and, since your elements don't have any prefix, it's the namespace your elements belong to; if they belonged to the other namespace you defined, i.e. xsi, their names would be e.g. xsi:sdnEntry.
Of course, since there's no default namespace in your first XML declaration but only the xsi namespace (which refers to a different URI), you would need to pass its URI to XName.Get and adapt your code.
In other words, you should make the URL parametric and pass it to your method, rather than hardcoding it like I did.
I tried your xml(s). I have used xml deserializer and it seems to work fine at my end. Please check the following code:
using System;
using System.Collections.Generic;
using System.Data;
using System.Data.SqlClient;
using System.IO;
using System.Reflection;
using System.Xml.Serialization;
using XML1;
using XML2;
namespace ConsoleApplication1
{
public class Program
{
private static void Main(string[] args)
{
var list1 = Deserialize<CONSOLIDATED_LIST>(#"CONSOLIDATED_LIST.xml"); // pass the path to your xml here
var list2 = Deserialize<List>(#"LIST.xml");
}
public static T Deserialize<T>(string path)
{
T obj;
XmlSerializer serializer = new XmlSerializer(typeof(T));
var reader = new StreamReader(path);
obj = (T)serializer.Deserialize(reader);
reader.Close();
return obj;
}
}
}
namespace XML1
{
[XmlRoot(ElementName = "INDIVIDUAL_ALIAS")]
public class INDIVIDUAL_ALIAS
{
[XmlElement(ElementName = "QUALITY")]
public string QUALITY { get; set; }
[XmlElement(ElementName = "ALIAS_NAME")]
public string ALIAS_NAME { get; set; }
}
[XmlRoot(ElementName = "INDIVIDUAL")]
public class INDIVIDUAL
{
[XmlElement(ElementName = "DATAID")]
public string DATAID { get; set; }
[XmlElement(ElementName = "VERSIONNUM")]
public string VERSIONNUM { get; set; }
[XmlElement(ElementName = "FIRST_NAME")]
public string FIRST_NAME { get; set; }
[XmlElement(ElementName = "SECOND_NAME")]
public string SECOND_NAME { get; set; }
[XmlElement(ElementName = "INDIVIDUAL_ALIAS")]
public List<INDIVIDUAL_ALIAS> INDIVIDUAL_ALIAS { get; set; }
}
[XmlRoot(ElementName = "INDIVIDUALS")]
public class INDIVIDUALS
{
[XmlElement(ElementName = "INDIVIDUAL")]
public INDIVIDUAL INDIVIDUAL { get; set; }
}
[XmlRoot(ElementName = "CONSOLIDATED_LIST")]
public class CONSOLIDATED_LIST
{
[XmlElement(ElementName = "INDIVIDUALS")]
public INDIVIDUALS INDIVIDUALS { get; set; }
[XmlAttribute(AttributeName = "xsi", Namespace = "http://www.w3.org/2000/xmlns/")]
public string Xsi { get; set; }
[XmlAttribute(AttributeName = "noNamespaceSchemaLocation", Namespace = "http://www.w3.org/2001/XMLSchema-instance")]
public string NoNamespaceSchemaLocation { get; set; }
[XmlAttribute(AttributeName = "dateGenerated")]
public string DateGenerated { get; set; }
}
}
namespace XML2
{
[XmlRoot(ElementName = "publshInformation", Namespace = "http://tempuri.org/List.xsd")]
public class PublshInformation
{
[XmlElement(ElementName = "Publish_Date", Namespace = "http://tempuri.org/List.xsd")]
public string Publish_Date { get; set; }
[XmlElement(ElementName = "Record_Count", Namespace = "http://tempuri.org/List.xsd")]
public string Record_Count { get; set; }
}
[XmlRoot(ElementName = "aka", Namespace = "http://tempuri.org/List.xsd")]
public class Aka
{
[XmlElement(ElementName = "category", Namespace = "http://tempuri.org/List.xsd")]
public string Category { get; set; }
[XmlElement(ElementName = "lastName", Namespace = "http://tempuri.org/List.xsd")]
public string LastName { get; set; }
[XmlElement(ElementName = "fisrtName", Namespace = "http://tempuri.org/List.xsd")]
public string FisrtName { get; set; }
}
[XmlRoot(ElementName = "akaList", Namespace = "http://tempuri.org/List.xsd")]
public class AkaList
{
[XmlElement(ElementName = "aka", Namespace = "http://tempuri.org/List.xsd")]
public List<Aka> Aka { get; set; }
}
[XmlRoot(ElementName = "sdnEntry", Namespace = "http://tempuri.org/List.xsd")]
public class SdnEntry
{
[XmlElement(ElementName = "lastName", Namespace = "http://tempuri.org/List.xsd")]
public string LastName { get; set; }
[XmlElement(ElementName = "fisrtName", Namespace = "http://tempuri.org/List.xsd")]
public string FisrtName { get; set; }
[XmlElement(ElementName = "akaList", Namespace = "http://tempuri.org/List.xsd")]
public AkaList AkaList { get; set; }
}
[XmlRoot(ElementName = "List", Namespace = "http://tempuri.org/List.xsd")]
public class List
{
[XmlElement(ElementName = "publshInformation", Namespace = "http://tempuri.org/List.xsd")]
public PublshInformation PublshInformation { get; set; }
[XmlElement(ElementName = "sdnEntry", Namespace = "http://tempuri.org/List.xsd")]
public SdnEntry SdnEntry { get; set; }
[XmlAttribute(AttributeName = "xsi", Namespace = "http://www.w3.org/2000/xmlns/")]
public string Xsi { get; set; }
[XmlAttribute(AttributeName = "xmlns")]
public string Xmlns { get; set; }
}
}
I personally would prefer the xml deserializer. It would be easy and more maintainable. Your underlying code, would remain the same and the deserialization can be done base on the Type T in your xml

How to Deserialize an xml element with only attributes in C#?

I am using System.Xml.Serialization.XmlSerializer class.I need to Deserialize the following XML in C#:
<message from="abc" to="xyz" xml:lang="en" id="Vx4Ix-14" type="chat">
<received xmlns="urn:xmpp:receipts" id="9beea4d7-aa1e-4f3c-929c-712b56164b63"/>
</message>
Following is my Class to deserialize it :
[XmlRoot(ElementName = "message")]
public class Message
{
[XmlAttribute(AttributeName = "type")]
public string Type { get; set; }
[XmlAttribute(AttributeName = "from")]
public string From { get; set; }
[XmlAttribute(AttributeName = "to")]
public string To { get; set; }
[XmlAttribute(AttributeName = "id")]
public string Id { get; set; }
[XmlAttribute(AttributeName = "xml:lang")]
public string Language { get; set; }
[XmlElement(ElementName = "received", Namespace = "urn:xmpp:receipts")]
public Received Received { get; set; }
}
public class Received
{
[XmlAttribute(AttributeName = "id")]
public string Id { get; set; }
}
The "received" xml element has only attributes and I want te deserialize that element to get "id" value of that element.
But when I use the above class to Deserialize , I get all the values except "id" attribute value of "received" xml element. I get the value of Received property as null.
Please let me know what is wrong with my class?
This is my Deserializer Method:
public static T Deserialize<T>(string xml)
{
T deserializedObject = default(T);
try
{
var serializer = new XmlSerializer(typeof(T));
using (var memoryStream = new MemoryStream(Encoding.UTF8.GetBytes(xml)))
{
deserializedObject = (T)serializer.Deserialize(memoryStream);
}
return deserializedObject;
}
catch (Exception)
{
return deserializedObject;
}
}
Your class looks good and also works for me. Maybe you're not using the deserializer correctly!? I successfully tried it with your XML like this:
var serializer = new XmlSerializer(typeof(Message));
var message = (Message)serializer.Deserialize(
new FileStream(#"C:\Users\homann.k\Desktop\test.xml", FileMode.Open, FileAccess.Read));

How to read XML file using XmlSerializer C# [duplicate]

This question already has an answer here:
Deserialization of xml file by using XmlArray?
(1 answer)
Closed 6 years ago.
I have a problem when I want to read XML file by using XmlSerializer.
My xml file like follow :
<?xml version="1.0" encoding="utf-8"?>
<contents>
<section id="1">
<element1>2</element1>
<element2>1</element2>
<idx>1</idx>
<idx>2</idx>
<idx>3</idx>
</section>
<section id="2">
<element1>2</element1>
<element2>1</element2>
</section>
<section id="3"/>
</contents>
Here are the classes:
[Serializable()]
public class section
{
[XmlAttribute("id")]
public string id { get; set; }
[XmlElement("element1")]
public int element1 { get; set; }
[XmlElement("element2")]
public int element2 { get; set; }
[XmlElement("idx")]
public int[] idx { get; set; }
}
[Serializable()]
[XmlRoot("contents")]
public class contents
{
[XmlArray("section")]
[XmlArrayItem("section", typeof(section))]
public section[] section { get; set; }
}
The Deserialize function:
XmlSerializer serializer = new XmlSerializer(typeof(contents));
FileStream fs = new FileStream(path, FileMode.Open);
XmlReader reader = XmlReader.Create(fs);
contents i;
i = (contents)serializer.Deserialize(reader);
fs.Close();
foreach (section p in i.section)
{
Console.WriteLine(p.element1);
}
Why it doesn't work?
I had reference https://msdn.microsoft.com/en-us/library/system.xml.serialization.xmlserializer(v=vs.110).aspx but it seem not useful.
Please help me!!!!!
Try this...
Usings...
using System.Collections.Generic;
using System.IO;
using System.Xml.Serialization;
Classes...(created from your XML using http://xmltocsharp.azurewebsites.net/)
[XmlRoot(ElementName = "section")]
public class Section
{
[XmlElement(ElementName = "element1")]
public string Element1 { get; set; }
[XmlElement(ElementName = "element2")]
public string Element2 { get; set; }
[XmlElement(ElementName = "idx")]
public List<string> Idx { get; set; }
[XmlAttribute(AttributeName = "id")]
public string Id { get; set; }
}
[XmlRoot(ElementName = "contents")]
public class Contents
{
[XmlElement(ElementName = "section")]
public List<Section> Section { get; set; }
}
Code...
Contents dezerializedXML = new Contents();
// Deserialize to object
XmlSerializer serializer = new XmlSerializer(typeof(Contents));
using (FileStream stream = File.OpenRead(#"xml.xml"))
{
dezerializedXML = (Contents)serializer.Deserialize(stream);
} // Put a break-point here, then mouse-over dezerializedXML
I put your XML in a file (xml.xml) and read it from there....

Categories