Arturs Kirsis
Arturs Kirsis

Reputation: 129

JSON error during parsing

Been looking for information on how to parse this json however everything I tried fails.

I am trying to parse JSON using this code:

var client = new WebClient();
client.Headers.Add("User-Agent", "Nobody");
var response = client.DownloadString(new Uri("https://api.worldoftanks.ru/wot/encyclopedia/tanks/?application_id=demo"));
Response asd = JsonConvert.DeserializeObject<Response>(response);

And I also have these classes set-up in a different file:

public class Response
{
    public string status { get; set; }
    public int count { get; set; }
    public List<Tank> data { get; set; }
}

public class Tank
{
    public string nation_i18n { get; set; }
    public string name { get; set; }
    public int level { get; set; }
    public string image { get; set; }
    public string image_small { get; set; }
    public string nation { get; set; }
    public bool is_premium { get; set; }
    public string type_i18n { get; set; }
    public string contour_image { get; set; }
    public string short_name_i18n { get; set; }
    public string name_i18n { get; set; }
    public string type { get; set; }
    public int tank_id { get; set; }
}

They are identical to data returned by the URL (please open it and you will see how it's built)

One thing I think is going wrong is that withing the "data" tag of the response instead of having a tag of "Tank" for each tank they actually named it as individual IDs. (again, please see URL for example)

Can anybody please help me with this? At the moment I am getting error:

An unhandled exception of type 'Newtonsoft.Json.JsonSerializationException' occurred in Newtonsoft.Json.dll Additional information: Cannot deserialize the current JSON object (e.g. {"name":"value"}) into type 'System.Collections.Generic.List`1[WotApp.Classes.Tank]' because the type requires a JSON array (e.g. [1,2,3]) to deserialize correctly. To fix this error either change the JSON to a JSON array (e.g. [1,2,3]) or change the deserialized type so that it is a normal .NET type (e.g. not a primitive type like integer, not a collection type like an array or List) that can be deserialized from a JSON object. JsonObjectAttribute can also be added to the type to force it to deserialize from a JSON object. Path 'data.1', line 1, position 39.

Hope for your help guys. I've been stuck with this for ages :(

Upvotes: 4

Views: 775

Answers (1)

Youp Bernoulli
Youp Bernoulli

Reputation: 5635

Was also looking and console-app testing for an answer and the comments of @Alexander and @dotctor are actually right answers ;) So your class will have to look like this:

public class Response
{
  public string status { get; set; }
  public int count { get; set; }
  public Dictionary<String, Tank> data { get; set; }
}

Here is another SO question dealing with exactly the same problem.

And my program listing:

namespace SO27839862
{
    class Program
    {
        static void Main(string[] args)
        {
            try
            {
                WebClient client = new WebClient();
                client.Headers.Add("User-Agent", "Nobody");

                String response = client.DownloadString(new Uri("https://api.worldoftanks.ru/wot/encyclopedia/tanks/?application_id=demo"));
                Response asd = JsonConvert.DeserializeObject<Response>(response);
            }
            catch (Exception ex)
            {

            }
        }
    }

    public class Response
    {
        public string status { get; set; }
        public int count { get; set; }
        public Dictionary<String, Tank> data { get; set; }
    }

    public class Tank
    {
        public string nation_i18n { get; set; }
        public string name { get; set; }
        public int level { get; set; }
        public string image { get; set; }
        public string image_small { get; set; }
        public string nation { get; set; }
        public bool is_premium { get; set; }
        public string type_i18n { get; set; }
        public string contour_image { get; set; }
        public string short_name_i18n { get; set; }
        public string name_i18n { get; set; }
        public string type { get; set; }
        public int tank_id { get; set; }
    }
}

Upvotes: 1

Related Questions