I have been working on an app using the Amazon affiliate API. I use a C# library (Nager.AmazonProductAdvertising) to make calls to the affiliate API but I am stuck.
The library doesn't include making variation matrix response group call to amazon affiliate API, so I had to use web request object to make the call. After making the call, the API returns an XML response, which I serialize to JSON. And then deserialize to a class.
The issue I am having is that sometimes the returned JSON can be have array or an object on variation attribute. I need help in writing a custom converter class to accept either an array or object on the same property.
Here are the two different sample JSON response.
{
"?xml": {
"@version": "1.0"
},
"ItemLookupResponse":
{
"@xmlns": "http://webservices.amazon.com/AWSECommerceService/2013-08-01",
"OperationRequest":
{
"RequestId": "d141ff28-2ef1-44a1-b2ce-97972f09ffcf",
"Arguments": {
"Argument": [
{
"@Name": "AWSAccessKeyId",
"@Value": "accessid"
},
{
"@Name": "AssociateTag",
"@Value": "mytag"
},
{
"@Name": "Condition",
"@Value": "All"
},
{
"@Name": "ItemId",
"@Value": "B01KIOU4EO"
},
{
"@Name": "Operation",
"@Value": "ItemLookup"
},
{
"@Name": "ResponseGroup",
"@Value": "VariationMatrix"
},
{
"@Name": "Timestamp",
"@Value": "2018-03-29T06:46:40Z"
},
{
"@Name": "Version",
"@Value": "2013-08-01"
},
{
"@Name": "http://webservices.amazon.com/onca/xml?Service",
"@Value": "AWSECommerceService"
},
{
"@Name": "Signature",
"@Value": "jhsjvhjvjsbjsonksljkksjb="
},
{
"@Name": "Service",
"@Value": "AWSECommerceService"
}
]
},
"RequestProcessingTime": "0.0053435950000000"
},
"Items": {
"Request": {
"IsValid": "True",
"ItemLookupRequest": {
"Condition": "All",
"IdType": "ASIN",
"ItemId": "B01KIOU4EO",
"ResponseGroup": "VariationMatrix",
"VariationPage": "All"
}
},
"Item": {
"ASIN": "B01KIOU4EO",
"ParentASIN": "B01KIOU4EO",
"Variations": {
"TotalVariations": "6",
"TotalVariationPages": "1",
"VariationDimensions": {
"VariationDimension": [
"Color",
"Configuration"
]
},
"Item": [
{
"ASIN": "B01J24C0TI",
"ItemAttributes": {
"Color": "Black"
},
"VariationAttributes": {
"VariationAttribute": [
{
"Name": "Configuration",
"Value": "Echo Show"
},
{
"Name": "Color",
"Value": "Black"
}
]
}
},
{
"ASIN": "B076C9DLGS",
"ItemAttributes": {
"Color": "Black"
},
"VariationAttributes": {
"VariationAttribute": [
{
"Name": "Configuration",
"Value": "Echo Show + Amazon Cloud Cam"
},
{
"Name": "Color",
"Value": "Black"
}
]
}
},
{
"ASIN": "B0767ZHCZG",
"ItemAttributes": {
"Color": "Black"
},
"VariationAttributes": {
"VariationAttribute": [
{
"Name": "Configuration",
"Value": "Show + Kasa Security Camera"
},
{
"Name": "Color",
"Value": "Black"
}
]
}
},
{
"ASIN": "B010CEHQTG",
"ItemAttributes": {
"Color": "White"
},
"VariationAttributes": {
"VariationAttribute": [
{
"Name": "Configuration",
"Value": "Echo Show"
},
{
"Name": "Color",
"Value": "White"
}
]
}
},
{
"ASIN": "B076C52ZPC",
"ItemAttributes": {
"Color": "White"
},
"VariationAttributes": {
"VariationAttribute": [
{
"Name": "Configuration",
"Value": "Echo Show + Amazon Cloud Cam"
},
{
"Name": "Color",
"Value": "White"
}
]
}
},
{
"ASIN": "B0767ZQZ3F",
"ItemAttributes": {
"Color": "White"
},
"VariationAttributes": {
"VariationAttribute": [
{
"Name": "Configuration",
"Value": "Show + Kasa Security Camera"
},
{
"Name": "Color",
"Value": "White"
}
]
}
}
]
}
}
}
}
}
Second response:
{
"?xml": {"@version": "1.0"
},
"ItemLookupResponse": {
"@xmlns": "http://webservices.amazon.com/AWSECommerceService/2013-08-01",
"OperationRequest": {
"RequestId": "207d197c-b29c-446f-a976-7dc9e37c5feb",
"Arguments": {
"Argument": [
{
"@Name": "AWSAccessKeyId",
"@Value": "accessid"
},
{
"@Name": "AssociateTag",
"@Value": "mytag"
},
{
"@Name": "Condition",
"@Value": "All"
},
{
"@Name": "ItemId",
"@Value": "B06X9FX834"
},
{
"@Name": "Operation",
"@Value": "ItemLookup"
},
{
"@Name": "ResponseGroup",
"@Value": "VariationMatrix"
},
{
"@Name": "Timestamp",
"@Value": "2018-03-29T06:35:22Z"
},
{
"@Name": "Version",
"@Value": "2013-08-01"
},
{
"@Name": "http://webservices.amazon.com/onca/xml?Service",
"@Value": "AWSECommerceService"
},
{
"@Name": "Signature",
"@Value": "kkkbkjkjsbjbisvuhjshshuvhs"
},
{
"@Name": "Service",
"@Value": "AWSECommerceService"
}
]
},
"RequestProcessingTime": "0.0105003370000000"
},
"Items": {
"Request": {
"IsValid": "True",
"ItemLookupRequest": {
"Condition": "All",
"IdType": "ASIN",
"ItemId": "B06X9FX834",
"ResponseGroup": "VariationMatrix",
"VariationPage": "All"
}
},
"Item": {
"ASIN": "B06X9FX834",
"ParentASIN": "B06X9FX834",
"Variations": {
"TotalVariations": "4",
"TotalVariationPages": "1",
"VariationDimensions": {
"VariationDimension": "Color"
},
"Item": [
{
"ASIN": "B01MZFKJL2",
"ItemAttributes": {
"Color": "black"
},
"VariationAttributes": {
"VariationAttribute": {
"Name": "Color",
"Value": "black"
}
}
},
{
"ASIN": "B01MUG5WIN",
"ItemAttributes": {
"Color": "blue"
},
"VariationAttributes": {
"VariationAttribute": {
"Name": "Color",
"Value": "blue"
}
}
},
{
"ASIN": "B01N5V0FVK",
"ItemAttributes": {
"Color": "grey"
},
"VariationAttributes": {
"VariationAttribute": {
"Name": "Color",
"Value": "grey"
}
}
},
{
"ASIN": "B01N284QCU",
"ItemAttributes": {
"Color": "red"
},
"VariationAttributes": {
"VariationAttribute": {
"Name": "Color",
"Value": "red"
}
}
}
]
}
}
}
}
}
this is the the class it is being deserialized to
using System;
using System.Collections.Generic;
using System.Net;
using System.Globalization;
using Newtonsoft.Json;
using Newtonsoft.Json.Converters;
using Newtonsoft.Json.Linq;
using System.Reflection;
namespace try
{
[JsonObject(MemberSerialization = MemberSerialization.OptIn)]
public class RootObject
{
[JsonProperty("?xml")]
public Xml Xml { get; set; }
[JsonProperty("ItemLookupResponse")]
public ItemLookupResponse ItemLookupResponse { get; set; }
}
public class Xml
{
[JsonProperty("@version")]
public string Version { get; set; }
}
public class ItemLookupResponse
{
[JsonProperty("@xmlns")]
public string Xmlns { get; set; }
[JsonProperty("OperationRequest")]
public OperationRequest OperationRequest { get; set; }
[JsonProperty("Items")]
public Items Items { get; set; }
}
public class OperationRequest
{
[JsonProperty("RequestId")]
public string RequestId { get; set; }
[JsonProperty("Arguments")]
public Arguments Arguments { get; set; }
[JsonProperty("RequestProcessingTime")]
public string RequestProcessingTime { get; set; }
}
public class Arguments
{
[JsonProperty("Argument")]
public List<Argument> Argument { get; set; }
}
public class Argument
{
[JsonProperty("@Name")]
public string Name { get; set; }
[JsonProperty("@Value")]
public string Value { get; set; }
}
public class Items
{
[JsonProperty("Request")]
public Request Request { get; set; }
[JsonProperty("Item")]
public Item Item { get; set; }
}
public class Request
{
[JsonProperty("IsValid")]
public string IsValid { get; set; }
[JsonProperty("ItemLookupRequest")]
public ItemLookupRequest ItemLookupRequest { get; set; }
}
public class ItemLookupRequest
{
[JsonProperty("Condition")]
public string Condition { get; set; }
[JsonProperty("IdType")]
public string IdType { get; set; }
[JsonProperty("ItemId")]
public string ItemId { get; set; }
[JsonProperty("ResponseGroup")]
public string ResponseGroup { get; set; }
[JsonProperty("VariationPage")]
public string VariationPage { get; set; }
}
public class Item
{
[JsonProperty("ASIN")]
public string ASIN { get; set; }
[JsonProperty("ParentASIN")]
public string ParentASIN { get; set; }
[JsonProperty("Variations")]
public Variations Variations { get; set; }
}
public class Variations
{
[JsonProperty("TotalVariations")]
public string TotalVariations { get; set; }
[JsonProperty("TotalVariationPages")]
public string TotalVariationPages { get; set; }
[JsonProperty("VariationDimensions")]
public VariationDimensions VariationDimensions { get; set; }
[JsonProperty("Item")]
public List<Item1> Item { get; set; }
}
public class VariationDimensions
{
[JsonProperty("VariationDimension")]
[JsonConverter(typeof(SingleOrArrayConverter<string>))]
public List<string> VariationDimension { get; set; }
}
public class Item1
{
[JsonProperty("ASIN")]
public string ASIN { get; set; }
[JsonProperty("ItemAttributes")]
public ItemAttributes ItemAttributes { get; set; }
[JsonProperty("VariationAttributes")]
public VariationAttributes VariationAttributes { get; set; }
}
public class ItemAttributes
{
[JsonProperty("Size")]
public string Size { get; set; }
}
public class VariationAttributes
{
[JsonConverter(typeof(SingleOrArrayConverter<string>))]
[JsonProperty("VariationAttribute")]
public List<VariationAttribute> VariationAttribute { get; set; }
}
public class VariationAttribute
{
[JsonProperty("Name")]
public string Name { get; set; }
[JsonProperty("Value")]
public string Value { get; set; }
}
}
class SingleOrArrayConverter<T> : JsonConverter
{
public override bool CanConvert(Type objectType)
{
return (objectType == typeof(List<T>));
}
public override object ReadJson(JsonReader reader, Type objectType, object existingValue,JsonSerializer serializer)
{
JToken token = JToken.Load(reader);
if (token.Type == JTokenType.Array)
{
return token.ToObject<List<T>>();
}
return new List<T> { token.ToObject<T>() };
}
public override bool CanWrite
{
get { return false; }
}
public override void WriteJson(JsonWriter writer,_
objectvalue,JsonSerializer serializer)
{
throw new NotImplementedException();
}
}