Как настроить ServiceStack.Text для использования EnumMember при десериализации?

Я использую ServiceStack.Text для десериализации JSON, полученных в остальных API-вызовов для объектов C#. Классы моделей, которые я использую, определили строковое представление, используя атрибуты EnumMember. Проблема в том, что ServiceStack.Text, похоже, не использует эти значения. В документации ServiceStack.Text есть раздел под названием Custom enum serialization, в котором обсуждается атрибут EnumMember, но в нем говорится только о сериализации без упоминания о десериализации.

Можно ли настроить ServiceStack.Text для использования EnumMember при десериализации перечислений?

Ниже приведен пример ситуации:

namespace TestNameSpace
{
    using System;
    using System.Runtime.Serialization;

    class TestClass
    {
        enum TestEnum
        {
            [EnumMember(Value = "default_value")]
            DefaultValue = 0,

            [EnumMember(Value = "real_value")]
            RealValue = 1
        }

        class TestEnumWrapper
        {
            public TestEnum EnumProperty { get; set; }

            public override string ToString()
            {
                return $"EnumProperty: {EnumProperty}";
            }
        }

        static void Main(string[] args)
        {
            string json = @"{ ""enumProperty"": ""real_value"" }";

            TestEnumWrapper deserialized =
                ServiceStack.Text.JsonSerializer.DeserializeFromString<TestEnumWrapper>(json);

            Console.WriteLine($"Deserialized: {deserialized}");
           // Prints: "Deserialized: EnumProperty: DefaultValue"
           // Expected: "Deserialized: EnumProperty: RealValue"
        }
    }
}

2 ответа

Решение

Я узнал, почему моя десериализация не работала. ServiceStack.Text не интерпретировал атрибуты EnumMember, поскольку объявление enum не имеет установленного атрибута DataContract. Это фактически объясняется в ссылке на документацию EnumMember, на которую я также ссылался в этом вопросе:

Одним из способов использования типов перечисления в модели контракта данных является применение атрибута DataContractAttribute к типу. Затем необходимо применить атрибут EnumMemberAttribute к каждому члену, который должен быть включен в контракт данных.

Ожидаемые результаты были получены путем добавления отсутствующего атрибута:

[DataContract] // This was missing
enum TestEnum
{ 
    // ...
}

Поддержка для [EnumMember] был добавлен только во время этого выпуска, так что вам нужно будет обновить до выпуска NuGe t v5.1.1 пакеты на MyGe t.

Другие вопросы по тегам