Debugging Serialization Exception: The constructor to deserialize an object was not found.
Today I was debugging an exception that was occuring when remoting a data object between two .NET processes. I kept getting
System.Runtime.Serialization.SerializationException: The constructor to deserialize an object of type 'com.TheSilentGroup.Fluorine.ASObject' was not found.
The issue I had was that there was a .NET object that looked like this
public class ItemDto{
public object Item { get;set; }
}
Which was used as a covariant store for any item (because everything is an object
). This was needed because the code I was working in leveraged reflection to pull out certain fields at runtime depending on whatever this object type really was.
But, at some point the ItemDto
object was sent to an ActionScript frontend. Later, the same object came back to .NET and the property Item
was now a ASObject
type due to Fluorine’s serialization process. Next, this object had to be serialized to another .NET process, and that’s where the exception was happening.
It was obvious that there was an issue with the ASObject
but I had assumed it was because the host process (that I was remoting to) didn’t have a reference to Fluorine’s dll to serialize the ASObject. But that wasn’t it.
Turns out that ASObject
inherits from HashTable
which implements ISerializable
.
From the MSDN
If a class needs to control its serialization process, it can implement the ISerializable interface. […] The ISerializable interface implies a constructor with the signature constructor (SerializationInfo information, StreamingContext context). At deserialization time, the current constructor is called only after the data in the SerializationInfo has been deserialized by the formatter. In general, this constructor should be protected if the class is not sealed.
So, because an interface can’t enforce a constructor signature, you have to make sure to implement this constructor on any object (even derived objects) if they are going to be serialized across .NET boundaries and implement ISerializable.
The solution, for me, was to just not send this object to the UI and back. It didn’t need to. But, you can overcome this issue by subclassing your data class, implementing the needed constructor, and calling the base class (in this case HashTable’s) constructor for proper serialization.