2

I'm using Json.NET (http://james.newtonking.com/projects/json/help/) as a way to serialize and deserialize JSON from a server. Let's say I have the following JSON object:

{
    "user" : {
         "name" : "Bob",
         "age" : 35
    },
    "location" : "California"
}

The only way that I can find to deserialize this in to native types is to use a custom DTO as follows:

string jsonString = ""; // json string from above
Response result = JsonConvert.DeserializeObject<Response> (jsonString);

where the Response class looks something like:

public class Response
{
    [JsonProperty("user")]
    public UserResponse User { get; set; }

    [JsonProperty("location")]
    public string Location { get; set; }
}

public class UserResponse
{
    [JsonProperty("name")]
    public string Name { get; set; }

    [JsonProperty("age")]
    public int Age { get; set; }
}

I want to deserialize this in to native types but I'm in an environment where I don't always know what the JSON string will look like... so it's hard to use custom DTO's when I don't know exactly what I'm getting down the pipe. If I don't pass any class in to JsonConvert.DeserializeObject(), then I end up with Json.NET types instead of native types like strings, ints, etc. Any suggestions on how to get around this? Should I be using a different JSON library instead?

Thanks!

4

1 回答 1

1

这不会解决您所有的问题(这是不可能的),但这里有一个解决方案,可以让您使用有限的返回信息来解析 json。

在外层,您创建一个对象,称为 Vehicle。这包含汽车、船和飞机。您正在请求一些车辆,但您不知道它是汽车、船还是飞机(请注意,这可以很容易地扩展为处理一系列车辆或许多其他更复杂的响应)。在架构中,您有一些选项,例如;

"id": "vehicle.schema.json",
"type": "object",
"required": true,
"additionalProperties": false,
"properties": {
    "Car": {
        "type": "object",
        "required": false
        //other properties
    },
              "Boat": {
        "type": "object",
        "required": false
        //other properties
    },
            "Plane": {
        "type": "object",
        "required": false
        //other properties
    }

以上是您将添加到项目中的架构文件。如果您想拥有其中的几个,只需将更多元组添加到下面的 _schemaTypes 数组中。

   // code to set up your schema
  // Associate types to their JsonSchemas.  Order matters here.
  // After each parse, the schema is added to resolver, which is used in subsequent parses.
        _schemaTypes = new[]
        {
            Tuple.Create(typeof(Vehicle), "vehicle.schema.json"),
        }
        .ToDictionary(
            x => x.Item1,
            x => JsonSchema.Parse(
                File.ReadAllText(
                    Path.Combine(AppDomain.CurrentDomain.RelativeSearchPath ?? "",  @"Serialization\Schemas\") + x.Item2),
                    resolver));


 //method to return your deserialized object
 public T Deserialize<T>(IRestResponse response)
    {
        var schema = _schemaTypes[typeof(T)];

        T result = _serializer.Deserialize<T>(
                new JsonValidatingReader(
                    new JsonTextReader(
                        new StringReader(response.Content)))
                {
                    Schema = schema
                });
        return result;
    }

现在,在您解析响应后,您将拥有一个更通用的对象,您可以从那里编写一些代码来确定返回的更具体的对象是什么。我正在使用这种类型的方法来解析 json,其中它具有多个级别的嵌套对象和对象数组,并且相当有效。

于 2012-11-09T23:24:48.277 回答