سؤال

My XML:

<result>
    <document version="2.1.0">
        <response type="currency">
            <currency>
                <code>AMD</code>
                <price>85.1366</price>
            </currency>
        </response>
        <response type="currency">
            <currency>
                <code>AUD</code>
                <price>31.1207</price>
            </currency>
        </response>
    </document>
</result>

My Class:

public class CurrencyData
{
    public string Code { get; set; }
    public string Price { get; set; }
}

My deserializer calling:

RestClient.ExecuteAsync<List<CurrencyData>>...

If i renamed class CurrencyData to Currency then all will been done right. But I want to keep this class name.

هل كانت مفيدة؟

المحلول

Ok, I think I got it,

You can try RestClient.ExecuteAsync<Result>()

[XmlRoot("result")]
public class Result
{
    [XmlElement("document")]
    public Document Document { get; set; }
}

public class Document 
{
    [XmlElement("response")]
    public Response[] Responses { get; set; }

    [XmlAttribute("version")]
    public string Version { get; set; }
}

public class Response
{
    [XmlElement("currency")]
    public CurrencyData Currency { get; set; }

    [XmlAttribute("type")]
    public string Type { get; set; }
}

public class CurrencyData
{
    [XmlElement("code")]
    public string Code { get; set; }

    [XmlElement("price")]
    public decimal Price { get; set; }
}

I had to add a few XmlElement attribute to override the casing without having to name classes and properties in lowercase. but you can drop them if you can change the xml to match the casing

نصائح أخرى

Answer of kay.one is perfect! It works with a any remarks:

public List<Response> Responses { get; set; }

works

public Response[] Responses { get; set; }

don`t works

And

[XmlElement("AnyValue")]

it is from System.Xml.Serialization namespace and don`t work. Feel free to just delete them. In this example annotation attributes and properties has same names and serializer understands. But right annotation attributes are from RestSharp.Deserializers namespace

    [DeserializeAs(Name="AnyXmlValue")]
    public string AnyModelValue { get; set; }

How to manage deserialization of RestSharp

Then change the xml tag to CurrencyData. Here is the documentation about the xml deserializer: https://github.com/restsharp/RestSharp/wiki/Deserialization

I'm not sure why Kay.one's answer is accepted, it doesn't answer the question.

Per my comment, the default RestSharp deserializer doesn't check for the DeserializeAs attribute when deserializing a list. I'm not sure if that's intentional or a mistake as the author doesn't seem to be very available.

Anyways it's a simple fix.

    private object HandleListDerivative(object x, XElement root, string propName, Type type)
    {
        Type t;

        if (type.IsGenericType)
        {
            t = type.GetGenericArguments()[0];
        }
        else
        {
            t = type.BaseType.GetGenericArguments()[0];
        }

        var list = (IList)Activator.CreateInstance(type);
        var elements = root.Descendants(t.Name.AsNamespaced(Namespace));

        var name = t.Name;

        //add the following
        var attribute = t.GetAttribute<DeserializeAsAttribute>();
        if (attribute != null)
            name = attribute.Name;
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top