【问题标题】:Deserializing json into object: wrapper class workaround将 json 反序列化为对象:包装类解决方法
【发布时间】:2015-08-24 14:07:14
【问题描述】:

这是我的 json

{
    "accessType":"Grant",
    "spaces":[{"spaceId":"5c209ba0-e24d-450d-8f23-44a99e6ae415"}],
    "privilegeId":"db7cd037-6503-4dbf-8566-2cca4787119d",
    "privilegeName":"PERM_RVMC_DEV",
    "privilegeDescription":"RVMC Dev",
    "privilegeType":"Permission"
}

这是我的课:

public class ProfilePrivilege
{
    public AccessType AccessType { get; set; }
    public Guid PrivilegeId { get; set; }
    public string PrivilegeName { get; set; }
    public string PrivilegeDescription { get; set; }
    public PrivilegeType PrivilegeType { get; set; }
    public List<Guid> spaces;
}

当空格数组不为空时,我得到一个反序列化错误。我可以通过简单地为 Guid 创建一个包装类来解决这个问题

public class Space
{
    public Guid spaceId;   
}

然后我可以在我的特权课程中使用List&lt;Space&gt; 而不是List&lt;Guid&gt;,这一切都很好。但我想知道是否有更好的方法来做到这一点,因为我不想为此而有一个冗余的包装类。那么有没有什么简单的方法可以在不为我的 Privilege 类型对象编写自定义反序列化程序的情况下解决这个问题?

顺便说一句,我正在使用 JSON.Net 反序列化。

【问题讨论】:

    标签: c# json serialization json.net


    【解决方案1】:

    您可以使用简单的JsonConverter 类将spaces 对象数组展平为GUID 列表,从而无需包装类。

    这是转换器所需的代码:

    class SpaceListConverter : JsonConverter
    {
        public override bool CanConvert(Type objectType)
        {
            return (objectType == typeof(List<Guid>));
        }
    
        public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
        {
            return JArray.Load(reader)
                         .Children<JObject>()
                         .Select(jo => Guid.Parse((string)jo["spaceId"]))
                         .ToList();
        }
    
        public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
        {
            throw new NotImplementedException();
        }
    }
    

    要使用它,请在 ProfilePrivilege 类中使用 [JsonConverter] 属性注释 Spaces 属性,如下所示:

    public class ProfilePrivilege
    {
        ...
        [JsonConverter(typeof(SpaceListConverter))]
        public List<Guid> Spaces;
        ...
    }
    

    然后,当您反序列化时,一切都应该“正常工作”。

    完整演示:https://dotnetfiddle.net/EaYgbe

    【讨论】:

      【解决方案2】:

      您不一定需要创建 POCO。另一种方法是使用动态:

      dynamic d = JObject.Parse(jsonString);
      
      Console.WriteLine(d.accessType);
      Console.WriteLine(d.spaces.Count);
      Console.WriteLine(d.spaces[0].spaceId);
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2017-06-04
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2016-10-08
        • 2017-12-19
        • 1970-01-01
        相关资源
        最近更新 更多