DeserializingException using SharpSerializer

2.7k Views Asked by At

I'm trying binary serialization to work with some complex objects. Using SharpSerializer, the serialization works without problems but I can't deserialize.

Here's the code snippet and the stack trace.

var settings = new SharpSerializerBinarySettings();
settings.IncludeAssemblyVersionInTypeName = true;
settings.IncludeCultureInTypeName = true;
settings.IncludePublicKeyTokenInTypeName = true;
settings.Mode = BinarySerializationMode.Burst;
var serializer = new SharpSerializer(settings);
using (IsolatedStorageFileStream isoStream = new IsolatedStorageFileStream(basePath + "current" + extension, FileMode.Open, isoStore))
{    
    try
    {
        result = serializer.Deserialize(isoStream) as MyObject;
        System.Diagnostics.Debug.WriteLine("loaded from " + basePath + "current" + extension);
     }
     catch (Exception ex)
     {
         System.Diagnostics.Debug.WriteLine(ex.Message);
     }
 }

stack:

  ex {Polenter.Serialization.Core.DeserializingException: An error occured during the deserialization.
   Details are in the inner exception. ---> System.TypeLoadException: Could not load type 'otContent ShowGridLines BackgroundColorARGBOpacity TransformMatrixM11M12M21M22Offs' from assembly 'Polenter.SharpSerializer.Silverlight, Version=2.18.0.0, Culture=neutral, PublicKeyToken=8f4f20011571ee5f'.
   at System.RuntimeTypeHandle.GetTypeByName(String name, Boolean throwOnError, Boolean ignoreCase, Boolean reflectionOnly, StackCrawlMarkHandle stackMark, IntPtr pPrivHostBinder, Boolean loadTypeFromPartialName, ObjectHandleOnStack type)
   at System.RuntimeTypeHandle.GetTypeByName(String name, Boolean throwOnError, Boolean ignoreCase, Boolean reflectionOnly, StackCrawlMark& stackMark, IntPtr pPrivHostBinder, Boolean loadTypeFromPartialName)
   at System.RuntimeType.GetType(String typeName, Boolean throwOnError, Boolean ignoreCase, Boolean reflectionOnly, StackCrawlMark& stackMark)
   at System.Type.GetType(String typeName, Boolean throwOnError)
   at Polenter.Serialization.Advanced.TypeNameConverter.ConvertToType(String typeName)
   at Polenter.Serialization.Advanced.BurstBinaryReader.ReadType()
   at Polenter.Serialization.Advanced.BinaryPropertyDeserializer.deserialize(Byte elementId, String propertyName, Type expectedType)
   at Polenter.Serialization.Advanced.BinaryPropertyDeserializer.deserialize(Byte elementId, Type expectedType)
   at Polenter.Serialization.Advanced.BinaryPropertyDeserializer.Deserialize()
   at Polenter.Serialization.SharpSerializer.Deserialize(Stream stream)
   --- End of inner exception stack trace ---
   at Polenter.Serialization.SharpSerializer.Deserialize(Stream stream)
   at MyNamespace.DataManager.MyMethod()}   System.Exception {Polenter.Serialization.Core.DeserializingException}

Im tying to deserialize a complex structure in which there is a hierarchy of custom controls and a lot of inheritance.

What's wrong with this code?

EDIT: Serialization code

var settings = new SharpSerializerBinarySettings();
settings.IncludeAssemblyVersionInTypeName = true;
settings.IncludeCultureInTypeName = true;
settings.IncludePublicKeyTokenInTypeName = true;
settings.Mode = BinarySerializationMode.Burst;
var serializer = new SharpSerializer(settings);   
using (IsolatedStorageFileStream isoStream = new IsolatedStorageFileStream(basePath + "current" + extension, FileMode.Create, isoStore))
{  
    serializer.Serialize(MyObject, isoStream);
    IsolatedStorageSettings.ApplicationSettings["saved"] = true;
    IsolatedStorageSettings.ApplicationSettings.Save();
    System.Diagnostics.Debug.WriteLine("Saved to " + basePath + "current" + extension);
}

The object that I'm trying to serialize/deserialize is something like this:

[DataContract]
public partial class MainObject : UserControl
{
    [IgnoreDataMember]
    private int zIndex = 10;

    [DataMember]
    private Dictionary<BasePlugin, Point> usedPlugins = new Dictionary<BasePlugin, Point>();

    ...methods...
}

where BasePlugin is a UserControl which is extended by other types. Here's the BasePlugin class

/// <summary>
/// Base class from which every plugin derives
/// </summary>
[DataContract]
public abstract partial class BasePlugin: UserControl
{

    [IgnoreDataMember]
    protected StackPanel settingsPanel;
    public StackPanel SettingsPanel
    {
        get
        {                
            if (settingsPanel == null)
            {
                settingsPanel = buildSettingsPanel();
            }
            return settingsPanel;
        }
    }

    [DataMember]
    protected Color backgroundColor = Color.FromArgb(255, 255, 255, 255);
    public Color BackgroundColor
    {
        get { return backgroundColor; }
        set { backgroundColor = value; }
    }

    [DataMember]
    protected Color foregroundColor = Color.FromArgb(255, 0, 0, 0);
    public Color ForegroundColor
    {
        get { return foregroundColor; }
        set { foregroundColor = value; }
    }

    [DataMember]
    protected string pluginName;
    public string PluginName
    {
        get { return pluginName; }
        protected set { pluginName = value; }
    }

    [DataMember]
    protected string pluginDescription;
    public string PluginDescription
    {
        get { return pluginDescription; }
        protected set { pluginDescription = value; }
    }

    [DataMember]
    protected Category pluginCategory;
    public Category PluginCategory
    {
        get { return pluginCategory; }
        protected set { pluginCategory = value; }
    }

    ...methods...
}

Just as a side info, running the SAME code of yesterday now leads to this message:

  Message "Error during creating an object. Please check if the type \"System.Windows.Markup.XmlLanguage, System.Windows, Version=2.0.6.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e\" has public parameterless constructor, or if the settings IncludeAssemblyVersionInTypeName, IncludeCultureInTypeName, IncludePublicKeyTokenInTypeName are set to true. Details are in the inner exception."  string
1

There are 1 best solutions below

0
On

You have a very complicated complex object on your hands that you want to (de)serialize. It seems simple from your standpoint but you inherit from an already complex object (UserControl). And SharpSerializer by default will serialize all public properties, no matter what. And this most probably leads to the problems you have.

Possible solutions:

  • Try (de)serializing just the information/properties you need in an object that is only meant for serialization. Then write some facility that converts between your serialization objects and your business objects (the ones you presented here).
  • Try configuring SharpSeralizer more so that you only store the properties you need (and also can serialize properly) and that work out of the box.