[Mono-devel-list] XML (de)serialization
Herscovici, Avi
AHerscovici at Empirix.com
Tue Jun 24 11:03:52 EDT 2003
First project with mono/mcs and I've run into a couple problems. I'm
getting incorrect output from (XML) deserializing when attributes are used.
Serializing with attributes gives the same xml file as .net produces, but
when deserializing, I get values from the default constructor and not the
ones I assigned to the members of the object before I serialized it. This
works fine if I don't have any attributes (such as [XMLAttribute]). Also,
trying to serialize an inherited class causes an unhandled
NullReferenceException to be thrown. Can someone fill me in as to the
status of xml serializing and deserializing? I am willing to contribute as
this is critical to my project (more critical is deserializing XML in mono
that is already serialized in .Net (windows)). Below are code examples for
which I obtain errors and the errors: (All of this is compiled with MCS
0.24 and run with mono 0.24)
-Avi
//------------------- serial-test.cs
----------------------------------------
// Test what objects mono can serialize and De-serialize.
using System;
using System.Xml.Serialization;
using System.IO;
using System.Xml;
using Test;
namespace Serial.test {
public class sertest {
public static void Save(System.IO.Stream stream, object x)
{
XmlSerializer ser = new
XmlSerializer(typeof(Script));
ser.Serialize(stream, x);
}
public static void Save(string filename, object x)
{
FileStream str = new FileStream(filename,
FileMode.Create, FileAccess.Write);
Save(str, x);
str.Close();
}
public static object Load(System.IO.Stream stream)
{
object s;
Console.WriteLine("Debug line 1a");
XmlSerializer ser = new
XmlSerializer(typeof(Script));
Console.WriteLine("Debug line 2a");
// try {
s = (object)ser.Deserialize(stream);
// }
// catch (Exception e) {Console.WriteLine("Exception: "
+ e);}
// s = null;
return s;
}
public static object Load(string filename)
{
object s;
Console.WriteLine("Debug line 2");
FileStream str = new FileStream(filename,
FileMode.Open, FileAccess.Read);
Console.WriteLine("Debug line 3");
s = Load(str);
Console.WriteLine("Debug line 4");
str.Close();
return s;
}
static void Main() {
string filename = "test.ser";
Script x = new Script();
x.X=0;
x.Y=1;
x.Z=2;
x.String="TEST";
x.Foo= new Bar();
x.Foo.I=10;
Save(filename, x);
Script temp = (Script)Load(filename);
Console.WriteLine("The values are: ");
Console.WriteLine(temp.X);
Console.WriteLine(temp.Y);
Console.WriteLine(temp.Z);
Console.WriteLine(temp.String);
Console.WriteLine(temp.Foo.I);
}
}
}
// ------------------------ test.cs -----------------------------
namespace Test
{
[XmlRoot(ElementName="Script", Namespace="http://www.foo.com")]
public class Script
{
// Vars
private int m_x;
private int m_y;
private int m_z;
private string m_str;
private Foo m_foo;
// Constructor
public Script()
{
m_x = -3;
m_y = -2;
m_z = -1;
m_str = null;
m_foo = null;
}
// Properties
[XmlIgnore()]
public int X
{
get { return m_x; }
set { m_x = value; }
}
[XmlAttribute("y")]
public int Y
{
get { return m_y; }
set { m_y = value; }
}
[XmlAttribute("z")]
public int Z
{
get { return m_z; }
set { m_z = value; }
}
[XmlAttribute("str")]
public string String
{
get { return m_str; }
set { m_str = value; }
}
public Foo Foo
{
get { return m_foo; }
set { m_foo = value; }
}
}
[XmlInclude(typeof(Bar))]
public class Foo
{
private int m_i;
public int I
{
get { return m_i; }
set { m_i = value; }
}
}
[XmlRoot("Bar", Namespace="http://www.foo.com")]
public class Bar : Foo
{
private int m_j;
public int J
{
get { return m_j; }
set { m_j = value; }
}
}
}
//------------------------------------------------- OUTPUT
----------------------------------------
output that I get when I run this in .Net:
Debug line 2
Debug line 3
Debug line 1a
Debug line 2a
Debug line 4
The values are:
-3
1
2
TEST
10
(which is correct, x.X has an ignore attribute)
under linux:
Unhandled Exception: System.NullReferenceException: A null value was found
where an object instance was required
in <0x00236> 00 System.Xml.Serialization.XmlSerializer:SerializeMembers
(System.Xml.XmlWriter,object,bool)
in <0x00795> 00 System.Xml.Serialization.XmlSerializer:WriteElement
(System.Xml.XmlWriter,System.Xml.Serialization.XmlAttributes,string,string,S
ystem.Type,object)
in <0x00eb1> 00 System.Xml.Serialization.XmlSerializer:SerializeMembers
(System.Xml.XmlWriter,object,bool)
in <0x00a02> 00 System.Xml.Serialization.XmlSerializer:Serialize
(System.Xml.XmlWriter,object,System.Xml.Serialization.XmlSerializerNamespace
s)
in <0x00071> 00 System.Xml.Serialization.XmlSerializer:Serialize
(System.IO.Stream,object)
in <0x00049> 00 Serial.test.sertest:Save (System.IO.Stream,object)
in <0x0004a> 00 Serial.test.sertest:Save (string,object)
in <0x00101> 00 Serial.test.sertest:Main ()
(concerning the incorrect output with attributes)
Now, if i comment out everything that has to do w/ Foo and Bar here is what
I get:
Debug line 2
Debug line 3
Debug line 1a
Debug line 2a
Debug line 4
The values are:
-3
-2
-1
(incorrect)
If I keep that commented out and also comment out all the attributes I get:
Debug line 2
Debug line 3
Debug line 1a
Debug line 2a
Debug line 4
The values are:
0
1
2
TEST
(which is the correct result)...
More information about the Mono-devel-list
mailing list