A long time ago I had to
implement some data storage between restartings of application in one of my
projects. I started looking for the best solution to do that and one of them using
.NET Settings files (about that I`ll write in the future), another – to use
serialization (I`ve chosen xml serialization because it is more human readable and flexible).
Serialization
is the process of converting an object into a stream of bytes in order to store
or
transmit it.
Deserialization is the opposite
process to serialization – converting data to object.
Want to know more about XML Serialization? Welcome...
Which class supports xml serialization?
In Binary serialization we make a
‘dump’ of appropriate object memory. At the time we can store all data along
with private properties and fields.
The most used serialization types in .NET Framework:
-
Binary
serialization (is the serialization process with binary data as a result)
- Xml serialization (is the serialization process with XML data as a result)
Want to know more about XML Serialization? Welcome...
Which class supports xml serialization?
XML Serialization uses
Reflection to get data from class to generate XML.
Therefore there are
next requirements for class that can be serialized to xml:- Class should contain public default constructor (without parameters).
- Only Public properties\fields are to be serialized.
- If public property is read-only then it value cannot be restored.
Now I`ll show to you how XML Serialization is easy to use .
Let’s take a look at our
test class.
public enum Role { RegularUser, Administrator }
public class User { public string Name { get; set; } public string EMail { get; set; } public string Password { get; set; } public int PasswordExpiresIn { get; set; } public int Age { get; set; } public Role UserRole { get; set; } }
Generic serialization and deserialization
Detailed information
about XMLSerializer can be found here in msdn: http://msdn.microsoft.com/en-us/library/system.xml.serialization.xmlserializer.aspx
I prefer developing some
abstract serializer which just gets some object (which will be serialized) and
returns xml result. It is very flexible because we separate serialization and
data saving. Thus if we need to store serialized object in database it cannot
be a problem and we shouldn’t improve serialization, we should only save it.Example:
public class Program { public static void Main(string[] args) { var userToSave = new User { Name = "Rostyslav", Age = 24, Password = "123", EMail = "sample@email.com", UserRole = Role.Administrator, }; var xml = XmlSerializationService<User>.Serialize(userToSave); Console.WriteLine(xml); } }
Result:
Manage 'class members to xml' transformation.
If you want to manage
serialization process: <User xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"> <Name>Rostyslav</Name> <Email>sample@email.com</Email> <Password>123</Password> <PasswordExpiresIn>0</PasswordExpiresIn> <Age>24</Age> <UserRole>Administrator</UserRole> </User>
Manage 'class members to xml' transformation.
- set the field that should be stored as xml-attribute;
- setup some another xml nodes name (instead of defaults based on members names);
Read more about Attributes that control XML Serialization here in msdn: http://msdn.microsoft.com/en-us/library/83y7df3e(v=vs.71).aspx
Now we can store and
restore our user object, but we want to change all nodes in result xml to
attributes, rename EMail attribute to UserMail and do not serialize PasswordExpiresIn property because these data will
be received from some another source. All that we need to do is only to set appropriate attributes to our target class.
Example:
Example:
public class User { [XmlAttribute] public string Name { get; set; } [XmlAttribute(AttributeName = "UserMail")] public string EMail { get; set; } [XmlAttribute] public string Password { get; set; } [XmlIgnore] public int PasswordExpiresIn { get; set; } [XmlAttribute] public int Age { get; set; } [XmlAttribute] public Role UserRole { get; set; } }
Result:
<User xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" Age="24" Name="Rostyslav" Password="123" UserMail="sample@email.com" UserRole="Administrator"> </User>
Serialization of complex/derived classes and arrays
If we derive classes
or some class that contains another one XmlSerializer will work fine. Also
XmlSerializer can serialize List<T> and arrays without any magic.
Example:
Result:
Result:
<?xml version="1.0" encoding="utf-16"?> <ArrayOfUser xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema"> <User Name="Rostyslav" UserMail="sample@email.com" Password="123" Age="24" UserRole="Administrator" /> <User Name="SomeAnotherGuy" UserMail="sample2@email.com" Password="qwerty" Age="42" UserRole="RegularUser" /> </ArrayOfUser>
Standard .NET class -
Dataset also supports xml serialization. In one of my projects I had to get
some data (without a strict structure) from one database and store these result
data in another one. I loaded all data into Dataset object and just serialized
to xml and saved it.
Summary
I think Xml
serialization is a nice .NET feature and it is really easy to use and fast to
implement. And you don’t have to parse manually XmlDocument anymore. Your code
will be more elegant and readable.
Yes, using XmlSerialization
is a bad idea when you try to use it with a huge amount of data, it will load
all data in the memory, but in the most common cases it is justified.
No comments:
Post a Comment