Search code examples
c#concurrent-collections

BlockingCollection default accessor


I am working with the BlockingCollection and have run into issues in attempting to serialize it. The error occurs on the new XmlSerializer line. The error is:

You must implement a default accessor on System.Collections.Concurrent.BlockingCollection`1[[BlockingCollTest.MyItem, BlockingCollTest, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null]] because it inherits from ICollection.

The test program is:

using System;
using System.Collections.Generic;
using System.Collections.Concurrent;
using System.IO;
using System.Xml;
using System.Xml.Serialization;

namespace BlockingCollTest
{
    class Program
    {
        static void Main(string[] args)
        {
            BlockingCollection<MyItem> c = new BlockingCollection<MyItem>();
            c.Add(new MyItem("001", "Smith"));
            c.Add(new MyItem("002", "Johnson"));

            XmlSerializer serializer = new XmlSerializer(typeof(BlockingCollection<MyItem>));
        }
    }
    [Serializable]
    public class MyItem
    {
        public string ID { get; set; }
        public string Name { get; set; }
        public MyItem() { }
        public MyItem(string id, string name) { ID = id; Name = name; }
    }
}

After trying several solutions and I am at a loss to understand how to solve this error.

Question: What is required to solve the serialization of a BlockingCollection issue?


Solution

  • BlockingCollection is not attributed as [Serializable] and does not implement ISerializable. Therefore you cannot serialize it using XmlSerializer even if MyItem is Serializable. You can copy the items to a single serializable collection or array (e.g. MyItem[]), serialize it and recreate the BlockingCollection after you deserialize back.