简体   繁体   中英

deserialise nested xml via json.net

I seem to have problems to deserialize this xml:

<Parameters>
    <AParameters>         
    </AParameters>
    <BParameters>       
    </BParameters>
</Parameters>

into:

public class Parameters
{
    public Parameters()
    {
        AParameters = new AParameters();
        BParameters = new BParameters();
    }

    public AParameters AParameters { get; set; }
    public BParameters BParameters { get; set; }
}

using these helpers:

public string TransformXmlStringToJsonString(string xmlString)
{
    try
    {
    var doc = new XmlDocument();
    doc.LoadXml(xmlString);
    return JsonConvert.SerializeXmlNode(doc);
    }
    catch (XmlException e)
    {
    throw new ArgumentException(string.Format("XML not well formed: {0}", e.Message));
    }   
}

public Parameters TransformXmlStringToParameters(string xmlString)
{
    var jsonString = TransformXmlStringToJsonString(xmlString);

    return DeserializeJsonString(jsonString);
}

private static Parameters DeserializeJsonString(string jsonString)
{
    return JsonConvert.DeserializeObject<Parameters>(jsonString);
}

The properties of AParameters and BParameters are not hydrated properly. Is there anything that I have to consider in this nested situation?

When you use JsonConvert.SerializeXmlNode(doc) to transform your XML document to a JSON string, the JSON that is generated looks like this:

{
    "?xml":
    {
        "@version":"1.0"
    },
    "Parameters":
    {
        "AParameters":
        {
            ...
        },
        "BParameters":
        {
            ...
        }
    }
}

Note that the Parameters data is not at the root, but is inside an outer object. So when you try to deserialize the JSON directly into a Parameters class, none of the properties line up because they are all one level further down. Since JSON.Net is unable to match up the field names in the class to the JSON data, it simply uses default values.

To fix this you can do one of two things.

1) Fix your XML to JSON transformation so that the Parameters data is at the root. To make it work the JSON data needs to look like this (below). This may be easier said than done.

{
    "AParameters":
    {
        ...
    },
    "BParameters":
    {
        ...
    }
}

2) Create a wrapper class and deserialize into that. This is much easier. For example:

class Wrapper
{
    public Parameters Parameters { get; set; }
}

Then deserialize like this:

Parameters p = JsonConvert.DeserializeObject<Wrapper>(jsonString).Parameters;

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM