Serializing an IDictionary object

Matt Berther bio photo By Matt Berther Comment

As of late, I really try to stay away from the XmlSerializer object, as I have found its limitations to be quite hindering in a lot of things I try to do.

One of the major drawbacks to this class is the serialization of an IDictionary based object. Every time that I need to do this, I end up looking towards Aaron Skonnard's column in the MSDN Magazine.

He details a fairly simple implementation that allows you to serialize an IDictionary by wrapping it in a custom object that implements IXmlSerializable.

I took his code and added a few convenience methods and present them here (mostly for my reference later). Enjoy!

class DictionarySerializer : IXmlSerializable
{
    private IDictionary dictionary;

    public DictionarySerializer()
    {
        this.dictionary = new Hashtable();
    }

    private DictionarySerializer(IDictionary dictionary)
    {
        this.dictionary = dictionary;
    }

    public static void Serialize(IDictionary dictionary, Stream stream)
    {
        DictionarySerializer ds = new DictionarySerializer(dictionary);
        XmlSerializer xs = new XmlSerializer(typeof(DictionarySerializer));
        xs.Serialize(stream, ds);
    }

    public static IDictionary Deserialize(Stream stream)
    {
        XmlSerializer xs = new XmlSerializer(typeof(DictionarySerializer));
        DictionarySerializer ds = (DictionarySerializer)xs.Deserialize(stream);
        return ds.dictionary;
    }

    XmlSchema IXmlSerializable.GetSchema()
    {
        return null;
    }

    void IXmlSerializable.ReadXml(XmlReader reader)
    {
        reader.Read();
        reader.ReadStartElement("dictionary");
        while (reader.NodeType != XmlNodeType.EndElement)
        {
            reader.ReadStartElement("item");
            string key = reader.ReadElementString("key");
            string value = reader.ReadElementString("value");
            reader.ReadEndElement();
            reader.MoveToContent();
            dictionary.Add(key, value);
        }
        reader.ReadEndElement();
    }

    void IXmlSerializable.WriteXml(XmlWriter writer)
    {
        writer.WriteStartElement("dictionary");
        foreach (object key in dictionary.Keys)
        {
            object value = dictionary[key];
            writer.WriteStartElement("item");
            writer.WriteElementString("key", key.ToString());
            writer.WriteElementString("value", value.ToString());
            writer.WriteEndElement();
        }
        writer.WriteEndElement();
    }
}