如何反序列化包含转义的JSON字符串的属性? [英] How do I deserialize a property containing an escaped JSON string?

查看:91
本文介绍了如何反序列化包含转义的JSON字符串的属性?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我从一个API收到一个application/json响应,该API本身具有一个包含转义的JSON字符串的属性.

I have an application/json response from an API that has a property, itself, containing an escaped JSON string.

{
    "id": 0,
    "aggregation_id": "533741f4-49da-4db9-9660-4ca7bafb30e1",
    "task_id": "217",
    "event_type": "discovery",
    "event_name": "device_discovery_complete",
    "method": "ssh",
    "message_details": "{\"aggregation_id\":\"533741f4-49da-4db9-9660-4ca7bafb30e1\",\"ou_id\":0,\"device_id\":13,\"node_id\":13,\"task_id\":217}",
    "time": "2018-01-25T17:59:25"
  }

我想反序列化对象和内部对象为模型类型.

I want to deserialize the object and the inner object to a model type.

public class Response
{
    public DateTime time {get; set;}
    public string event_name {get; set;}
    public string event_type {get; set;}
    public string method {get; set;}
    public MessageDetails message_details {get; set;}
}

public class MessageDetails
{
    public int device_id {get; set;}
}

使用这样的通话

JsonConvert.DeserializeObject<Response>("... response string...");

但是,Netwonsoft.Json可以很好地处理外部属性,但是在匹配message_details时会引发异常.

However, Netwonsoft.Json handles the outer properties just fine, but throws an exception on matching message_details.

Newtonsoft.Json.JsonSerializationException: Error converting value "... response string snipped ..." to type 'RpcApi.Entities.MessageDetails'. 
Path '[0].message_details', line 1, position 390. 
---> System.ArgumentException: Could not cast or convert from System.String to RpcApi.Entities.MessageDetails.

推荐答案

为此,您可以使用自定义JsonConverter:

You could use a custom JsonConverter for this similar to this:

public class EmbeddedJsonConverter : JsonConverter
{
    public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
    {
        throw new NotImplementedException();
    }

    public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer)
    {
        return serializer.Deserialize(new StringReader((string)reader.Value), objectType);
    }

    public override bool CanConvert(Type objectType)
    {
        return true;
    }
}

使用[JsonConverter(typeof(EmbeddedJsonConverter))]标记属性,例如:

public class Response
{
    public DateTime time { get; set; }
    public string event_name { get; set; }
    public string event_type { get; set; }
    public string method { get; set; }

    [JsonConverter(typeof(EmbeddedJsonConverter))]
    public MessageDetails message_details { get; set; }
}

然后您将可以使用JsonConvert.DeserializeObject<Response>()反序列化.

Then you will be able to deserialize with JsonConvert.DeserializeObject<Response>().

EmbeddedJsonConverter类从对象中提取json字符串,然后反序列化.对于真正的通用用途,应该使CanConvert更聪明.

The EmbeddedJsonConverter class extracts the json string from the object and then deserializes it. CanConvert should probably be made smarter for a truly generic use.

这篇关于如何反序列化包含转义的JSON字符串的属性?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆