Невозможно десериализовать классы с несколькими конструкторами с помощью Json.NET

У меня есть тип, который я не контролирую с несколькими конструкторами, эквивалентными этому:

    public class MyClass
    {
        private readonly string _property;

        private MyClass()
        {
            Console.WriteLine("We don't want this one to be called.");
        }

        public MyClass(string property)
        {
            _property = property;
        }

        public MyClass(object obj) : this(obj.ToString()) {}

        public string Property
        {
            get { return _property; }
        }

    }

Теперь, когда я пытаюсь десериализовать его, вызывается частный без параметров constuctor и свойство никогда не устанавливается. Тест:

    [Test]
    public void MyClassSerializes()
    {
        MyClass expected = new MyClass("test");
        string output = JsonConvert.SerializeObject(expected);
        MyClass actual = JsonConvert.DeserializeObject<MyClass>(output);
        Assert.AreEqual(expected.Property, actual.Property);
    }

дает следующий результат:

We don't want this one to be called.

  Expected: "test"
  But was:  null

Как я могу исправить это, не изменяя определение MyClass? Кроме того, этот тип является ключом к глубокому определению объектов, которые мне действительно нужны для сериализации.

Ответ 1

Попробуйте добавить атрибут [JsonConstructor] к конструктору, который вы хотите использовать при десериализации.

Измените это свойство в своем классе:

[JsonConstructor]
public MyClass(string property)
{
    _property = property;
}

Я только что попробовал, и ваш тест проходит: -)

Если вы не можете сделать это изменение, я думаю, вам нужно создать CustomJsonConverter. http://james.newtonking.com/json/help/index.html?topic=html/CustomJsonConverter.htm и Как реализовать пользовательский JsonConverter в JSON.NET для десериализации списка базового класса объекты? могут помочь.

Вот полезная ссылка для создания CustomJsonConverter: fooobar.com/info/78659/...