1

I am making an Api request in my Xamarin.forms app, the request is to display list of stores but it's throwing the following exception : Cannot deserialize the current JSON object (e.g. {"name":"value"}) into type 'System.Collections.Generic.List`1[LoyaltyWorx.Page1+Store]' because the type requires a JSON array (e.g. [1,2,3]) to deserialize correctly.

Json response:

{
    "Credentials": {
        "Token": "K6Zi8VXfqWuthxgn3YEfrU6Bj/EKM7BqvSZcatFgvMx408yadbE+Qj6IuTnZ++C9q4Ty1W2f1quNYMKZxFBNZg==",
        "Authenticated": true,
        "SecretKey": null
    },
    "Companies": [
        {
            "CustomerID": 2,
            "CompanyName": "Posworx",
            "CompanyLogo": "\Images\\Capture.JPG",
            "Stores": [
                {
                    "StoreID": 2,
                    "StoreNumber": null,
                    "StoreName": "Pos Store",
                    "StoreAddress": "218 Stamford Hill Road",
                    "StoreCity": "Durban",
                    "StoreRegion": "KZN",
                    "StoreCountry": "South Africa"
                },
                {
                    "StoreID": 4,
                    "StoreNumber": null,
                    "StoreName": "Pos Store",
                    "StoreAddress": "218 Mathews Meyiwa Road",
                    "StoreCity": "Durban",
                    "StoreRegion": "KZN",
                    "StoreCountry": "South Africa"
                }
]
        },

Class in Xamarin.Forms:

 public class Store
        {
            public List<Company> companies { get; set; }
            public int StoreID { get; set; }
            public object StoreNumber { get; set; }
            public string StoreName { get; set; }
            public string StoreAddress { get; set; }
            public string StoreCity { get; set; }
            public string StoreRegion { get; set; }
            public string StoreCountry { get; set; }
        }
        public class Credentials
        {
            public string Token { get; set; }
            public bool Authenticated { get; set; }
            public object SecretKey { get; set; }
        }
        public class Company
        {
            public int CustomerID { get; set; }
            public string CompanyName { get; set; }
            public string CompanyLogo { get; set; }
            public IList<Store> Stores { get; set; }
        }

        public class Stores
        {
            public Credentials Credentials { get; set; }
            public IList<Company> Companies { get; set; }
            public bool IsError { get; set; }
            public object ErrorMessage { get; set; }
        }

The code to load and deserialize the response:

public async void LoadData()
{
    try
    {
        var content = "";
        HttpClient client = new HttpClient();
        var RestUrl = "/api/Company/GetCustomerCompanies";
        client.BaseAddress = new Uri(RestUrl);

        client.DefaultRequestHeaders.Add("X-Giftworx-App", "K6Zi8VXfqWuthxgn3YEfrU6Bj/EKM7BqvSZcatFgvMx408yadbE+Qj6IuTnZ++C9q4Ty1W2f1quNYMKZxFBNZg==");
        HttpResponseMessage response = await client.GetAsync(RestUrl);
        content = await response.Content.ReadAsStringAsync();
        var Items = JsonConvert.DeserializeObject<List<Store>>(content);
        MainListView.ItemsSource = Items;
    }


    catch (Exception ex)
    {
        string exception = ex.Message;
    }

}

The objective is to display CompanyName and CompanyLogo in the ListView: Xaml:

<ListView Grid.Column="0" Grid.Row="0"
                  x:Name="MainListView"
                  HasUnevenRows="True" 
                  VerticalOptions="FillAndExpand"
                  HorizontalOptions="FillAndExpand"
                  ItemTapped="MainListView_ItemTapped" 
                  SeparatorColor="DarkGray">
            <ListView.ItemTemplate>
                <DataTemplate>
                    <ImageCell ImageSource="{Binding CompanyLogo}" 
                               Text="{Binding CompanyName}" 
                               TextColor="Black"
                              />
                </DataTemplate>
            </ListView.ItemTemplate>
        </ListView>
Paul Kertscher
  • 9,416
  • 5
  • 32
  • 57

1 Answers1

1

You are trying to serialize the JSON into a List<Store>. Anyway, the JSON you provided is not an array (as the exception stated), but is a single Store. You'll have to deserialize it into a Store object to work properly.

With Json.NET you can achieve this with

var store = JsonConvert.DeserializeObject<Store>(jsonResponse);

Edit:

After trying to understand your snippets better I came to the conclusion, that

var stores = JsonConvert.DeserializeObject<Stores>(jsonResponse); 

could be more what you need, than the first snippet. The JSON response looks rather like the Stores class than the Store class.

Edit 2:

The JSON was not correct, I removed the comma at the end and added a ] and a } to make it valid.

{
    "Credentials": {
        "Token": "K6Zi8VXfqWuthxgn3YEfrU6Bj/EKM7BqvSZcatFgvMx408yadbE+Qj6IuTnZ++C9q4Ty1W2f1quNYMKZxFBNZg==",
        "Authenticated": true,
        "SecretKey": null
    },
    "Companies": [{
            "CustomerID": 2,
            "CompanyName": "Posworx",
            "CompanyLogo": "\Images\\Capture.JPG",
            "Stores": [{
                    "StoreID": 2,
                    "StoreNumber": null,
                    "StoreName": "Pos Store",
                    "StoreAddress": "218 Stamford Hill Road",
                    "StoreCity": "Durban",
                    "StoreRegion": "KZN",
                    "StoreCountry": "South Africa"
                }, {
                    "StoreID": 4,
                    "StoreNumber": null,
                    "StoreName": "Pos Store",
                    "StoreAddress": "218 Mathews Meyiwa Road",
                    "StoreCity": "Durban",
                    "StoreRegion": "KZN",
                    "StoreCountry": "South Africa"
                }
            ]
        }
    ]
}

Deserializing this fixed JSON to Stores (second snippet) worked for me.

Paul Kertscher
  • 9,416
  • 5
  • 32
  • 57