首页 > 解决方案 > 根据返回的状态码将 JSON 对象反序列化为字符串或具体类型

问题描述

这是我的Rootobject课程,由 VS 中的“特殊粘贴”生成。

public class Rootobject
{
    public string formatVersion { get; set; }
    public Matrix[][] matrix { get; set; }
    public Summary summary { get; set; }
}

public class Summary
{
    public int successfulRoutes { get; set; }
    public int totalRoutes { get; set; }
}

public class Matrix
{
    public int statusCode { get; set; }
    public object response { get; set; }
    public Detailederror detailedError { get; set; }
}

public class Detailederror
{
    public string message { get; set; }
    public string code { get; set; }
}

这是根据以下模型建模的:

{
    "formatVersion": "0.0.1",
    "matrix": [
        [
            {
                "statusCode": 200,
                "response": {
                    "routeSummary": {
                        "lengthInMeters": 95028,
                        "travelTimeInSeconds": 4581,
                        "trafficDelayInSeconds": 0,
                        "trafficLengthInMeters": 0,
                        "departureTime": "2021-10-03T09:48:17+01:00",
                        "arrivalTime": "2021-10-03T11:04:38+01:00"
                    }
                }
            },
            {
                "statusCode": 200,
                "response": {
                    "routeSummary": {
                        "lengthInMeters": 97955,
                        "travelTimeInSeconds": 4928,
                        "trafficDelayInSeconds": 0,
                        "trafficLengthInMeters": 0,
                        "departureTime": "2021-10-03T09:48:17+01:00",
                        "arrivalTime": "2021-10-03T11:10:25+01:00"
                    }
                }
            }
        ],
        [
            {
                "statusCode": 200,
                "response": {
                    "routeSummary": {
                        "lengthInMeters": 105077,
                        "travelTimeInSeconds": 4725,
                        "trafficDelayInSeconds": 0,
                        "trafficLengthInMeters": 0,
                        "departureTime": "2021-10-03T09:48:17+01:00",
                        "arrivalTime": "2021-10-03T11:07:01+01:00"
                    }
                }
            },
            {
                "statusCode": 200,
                "response": {
                    "routeSummary": {
                        "lengthInMeters": 108004,
                        "travelTimeInSeconds": 5072,
                        "trafficDelayInSeconds": 0,
                        "trafficLengthInMeters": 0,
                        "departureTime": "2021-10-03T09:48:17+01:00",
                        "arrivalTime": "2021-10-03T11:12:48+01:00"
                    }
                }
            }
        ],
        [
            {
                "statusCode": 200,
                "response": {
                    "routeSummary": {
                        "lengthInMeters": 103661,
                        "travelTimeInSeconds": 4624,
                        "trafficDelayInSeconds": 0,
                        "trafficLengthInMeters": 0,
                        "departureTime": "2021-10-03T09:48:17+01:00",
                        "arrivalTime": "2021-10-03T11:05:21+01:00"
                    }
                }
            },
            {
                "statusCode": 200,
                "response": {
                    "routeSummary": {
                        "lengthInMeters": 106588,
                        "travelTimeInSeconds": 4971,
                        "trafficDelayInSeconds": 0,
                        "trafficLengthInMeters": 0,
                        "departureTime": "2021-10-03T09:48:17+01:00",
                        "arrivalTime": "2021-10-03T11:11:08+01:00"
                    }
                }
            }
        ],
        [
            {
                "statusCode": 400,
                "response": "Engine error while executing route request: MAP_MATCHING_FAILURE: Origin (0, 0)",
                "detailedError": {
                    "message": "Engine error while executing route request: MAP_MATCHING_FAILURE: Origin (0, 0)",
                    "code": "MAP_MATCHING_FAILURE"
                }
            },
            {
                "statusCode": 400,
                "response": "Engine error while executing route request: MAP_MATCHING_FAILURE: Origin (0, 0)",
                "detailedError": {
                    "message": "Engine error while executing route request: MAP_MATCHING_FAILURE: Origin (0, 0)",
                    "code": "MAP_MATCHING_FAILURE"
                }
            }
        ]
    ],
    "summary": {
        "successfulRoutes": 6,
        "totalRoutes": 8
    }
}

但是,对于列表中的每个项目,对象的状态代码Matrix可以是 200 OK 或 400。

public class Matrix
{
    public int statusCode { get; set; }
    public object response { get; set; }
    public Detailederror detailedError { get; set; }
}

如果是 200,则response对象将是Routesummary.

public class Routesummary
{
    public int lengthInMeters { get; set; }
    public int travelTimeInSeconds { get; set; }
    public int trafficDelayInSeconds { get; set; }
    public int trafficLengthInMeters { get; set; }
    public DateTime departureTime { get; set; }
    public DateTime arrivalTime { get; set; }
}

但是,如果它是 400,则该response对象将是字符串格式的错误消息。

{
   "statusCode":400,
   "response":"Engine error while executing route request: MAP_MATCHING_FAILURE: Origin (0, 0)",
   "detailedError":{
      "message":"Engine error while executing route request: MAP_MATCHING_FAILURE: Origin (0, 0)",
      "code":"MAP_MATCHING_FAILURE"
   }
}

我正在使用JsonConvert.DeserializeObject<rootobject>,但我遇到的问题是,如果我更改结构以保存 Routesummary,则 400 响应的反序列化将失败 - 这将是一个字符串。

我不确定如何根据 JSON 检查响应代码,然后告诉反序列化器根据响应反序列化为字符串/对象。

我正在调用 Azure Maps API(矩阵路由)。

标签: c#jsonserialization

解决方案


使用这个版本的Matrix- 带有responseset 作为通用对象的版本 - 用于反序列化。

这将允许您在 400 的情况下获取一个字符串,在Routesummary200 的情况下获取一个对象,而不会引发任何异常。

public class Matrix
{
    public int statusCode { get; set; }
    public object response { get; set; }
    public Detailederror detailedError { get; set; }
}

反序列化后,对状态代码进行简单检查,并根据它是否成功,适当地进行转换。

if (matrix.statusCode is 200) {
    var routeSummary = (Routesummary)matrix.Response;
    ...
}
else {
    var errorMessage = (string)matrix.Response;
    var detailedError = matrix.detailedError;
    ...
}

希望这可以帮助。


推荐阅读