Deserialize a GSON generated JSON string n C# - c#

I have a JSON generated through java using GSON. I want to recreate the same fields in C#. The JSON looks something like this.
{
"bool1": true,
"long1": 0,
"double1": 500.0,
"int1": 1,
"double2": 0.4,
"double3": 0.3,
"double4": 1.0,
"double5": 0.1,
"int2": 0,
"int3": 0,
"long2": 20160901,
"class1object1": {
"serialVersionUID": 1,
"class1int1": 0,
"class1int2": 0,
"class1int3": 0,
"class1double1": 68.3,
"class1doubleArray1": [68.3],
"class1double2": 65.45,
"class1doubleArray2": [65.45],
"class1int4": 1
},
"class1object2": {
"serialVersionUID": 1,
"class1int1": 135,
"class1int2": 138,
"class1int3": 105,
"class1double1": 68.1,
"class1doubleArray1": [67.57, 67.6, 67.48, 67.45, 67.39, 67.42, 67.38, 67.37, 67.35, 67.35, 67.37, 67.35, 67.36, 67.37, 67.35, 67.37, 67.38],
"class1double2": 67.26,
"class1doubleArray2": [67.5, 67.53, 67.46, 67.4, 67.39, 67.38, 67.37, 67.32, 67.33, 67.33, 67.33, 67.35, 67.36, 67.33, 67.33, 67.37, 67.34],
"class1int4": 240
},
"int4": 1,
"class2object1": {
"serialVersionUID": 1,
"class2double1": 2.8499999999999943,
"class2double2": 1.6758422688703467,
"class2double3": 0.09523809523809523
},
}
The definitions for all these classes and other fields are already there in my C# application. Also if required, the names of fields can be kept the same as they are in the JSON.
Can someone please help me with what tool should I use in order to achieve this and how? Also there is a possibility of NaN/Inf values as well (Secondary problem, not very important and can be omitted from JSON if required.

You can use JSON2CSHARP or copy json to clipboard > go to Visual Studio > Edit>Paste Special>Paste JSON as Classes. It's give you model classes. Uisng Newtonsoft.Json package you can deserialize your json:
JsonConvert.DeserializeObject<RootClassName>("json");
Your model class should look:
public class Class1
{
public int serialVersionUID { get; set; }
public int class1int1 { get; set; }
public int class1int2 { get; set; }
public int class1int3 { get; set; }
public double class1double1 { get; set; }
public List<double> class1doubleArray1 { get; set; }
public double class1double2 { get; set; }
public List<double> class1doubleArray2 { get; set; }
public int class1int4 { get; set; }
}
public class Class2
{
public int serialVersionUID { get; set; }
public int class1int1 { get; set; }
public int class1int2 { get; set; }
public int class1int3 { get; set; }
public double class1double1 { get; set; }
public List<double> class1doubleArray1 { get; set; }
public double class1double2 { get; set; }
public List<double> class1doubleArray2 { get; set; }
public int class1int4 { get; set; }
}
public class Class3
{
public int serialVersionUID { get; set; }
public double class2double1 { get; set; }
public double class2double2 { get; set; }
public double class2double3 { get; set; }
}
public class RootObject
{
public bool bool1 { get; set; }
public int long1 { get; set; }
public double double1 { get; set; }
public int int1 { get; set; }
public double double2 { get; set; }
public double double3 { get; set; }
public double double4 { get; set; }
public double double5 { get; set; }
public int int2 { get; set; }
public int int3 { get; set; }
public int long2 { get; set; }
public Class1 Class1 { get; set; }
public Class2 Class2 { get; set; }
public int int4 { get; set; }
public Class3 Class3 { get; set; }
}
Also if you want use others name in C# classes you need use JsonProperty(PropertyName = "yourJsonName"),this allows you to specify a different name this example should help:
public class Foo
{
[JsonProperty(PropertyName = "fooJSONname")]
public int FooNumber { get; set; }
}

Related

Sending 2 Lists In A Class From Postman

these are my classes.
public class BasketClass
{
public int HowMany { get; set; }
public int MBasketId { get; set; }
public int MVendorId { get; set; }
public int WInvestorId { get; set; }
public int MProductId { get; set; }
}
public class VendorPay
{
public int id { get; set; }
public int MVendorId { get; set; }
public bool IsCargoIncluded { get; set; }
public decimal CargoAmount { get; set; }
public decimal TotalAmount { get; set; }
}
public class PayBasketInputClass
{
public List<BasketClass> mOrderList { get; set; }
public List<VendorPay> vendorPayList { get; set; }
}
And this is my method.
public IActionResult PayBasket(int WInvestorId, PayBasketInputClass payInput, string paymenttype)
I gotta send payInput from body. But it includes two lists and its to complicated for me. Can you help me how to do it with an example?
Cheers.
{
"mOrderList": [
{
"HowMany": 1,
"MBasketId": 2,
"MVendorId": 3,
"WInvestorId": 4,
"MProductId": 5
}
],
"vendorPayList": [
{
"id": 1,
"MVendorId": 2,
"IsCargoIncluded": true,
"CargoAmount": 3.99,
"TotalAmount": 4.99
}
]
}
Json object is above is your PayBasketInputClass object in json structure.

Deserialize JSON to a class (Newtonsoft, C#)

I am trying to save JSON data into my Class. I've tried different ways but didn't succeed.
Here is my class:
class YoCurrency
{
public string Currency { get; set; }
public double high { get; set; }
public double low { get; set; }
public double avg { get; set; }
public double vol { get; set; }
[JsonProperty("vol_cur")]
public double vol_cur { get; set; }
public double last { get; set; }
public double buy { get; set; }
public double sell { get; set; }
public int updated { get; set; }
}
Here is JSON file.
Trying to deserialize with generic List:
List<YoCurrency> a = JsonConvert.DeserializeObject<List<YoCurrency>>(json);
gives an error:
Newtonsoft.Json.JsonSerializationException: 'Cannot deserialize the current JSON object (e.g. {"name":"value"}) into type 'System.Collections.Generic.List`1[YoBitParser.YobitCurrency]' 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 'btc_usd', line 1, position 11.'
Deserializing this way:
var a = JsonConvert.DeserializeObject<YobitCurrency>(json);
Doesn't give any result, because all class fields get 0 value
Also I tried to use two classes like this:
class YoCurrency
{
public double high { get; set; }
public double low { get; set; }
public double avg { get; set; }
public double vol { get; set; }
[JsonProperty("vol_cur")]
public double vol_cur { get; set; }
public double last { get; set; }
public double buy { get; set; }
public double sell { get; set; }
public int updated { get; set; }
}
class YoPair
{
YoCurrency Currency { get; set; }
string Name { get; set; }
}
But it didn't give any positive result. I tried to generate c# classes using http://json2csharp.com, but it generates a class for every currency:
public class BtcUsd
{
public double high { get; set; }
public double low { get; set; }
public double avg { get; set; }
public double vol { get; set; }
public double vol_cur { get; set; }
public double last { get; set; }
public double buy { get; set; }
public double sell { get; set; }
public int updated { get; set; }
}
public class EthUsd
{
...
}
public class RootObject
{
public BtcUsd btc_usd { get; set; }
public EthUsd eth_usd { get; set; }
...
}
But i suppose it's not good way in case of 50 or 500 pairs (or should I create a unique class for every currency?)
So please help me to deserialize this JSON or give me some information that could help me to solve this problem.
Why not just make one class?
class Program
{
static void Main(string[] args)
{
var array = "[{\"btc_usd\":[{\"high\":8550.0102,\"low\":7800,\"avg\":8175.0051,\"vol\":1615543.57397705,\"vol_cur\":197.54076079,\"last\":7850,\"buy\":7850.00000000,\"sell\":7879.00000000,\"updated\":1521383863}],\"eth_usd\":[{\"high\":622.93708559,\"low\":482,\"avg\":552.46854279,\"vol\":346598.40520112,\"vol_cur\":630.37075493,\"last\":488.27857735,\"buy\":489.77564548,\"sell\":492.11726255,\"updated\":1521383876}]}]";
List<RootObject> a = JsonConvert.DeserializeObject<List<RootObject>>(array);
}
}
public class RootCurrency
{
public double high { get; set; }
public int low { get; set; }
public double avg { get; set; }
public double vol { get; set; }
public double vol_cur { get; set; }
public double last { get; set; }
public double buy { get; set; }
public double sell { get; set; }
public int updated { get; set; }
}
public class RootObject
{
public List<RootCurrency> btc_usd { get; set; }
public List<RootCurrency> eth_usd { get; set; }
}
It look like your class structure is not proper, suggest you to generate class with the help of Visual Studio like as below and try your code by using generated class
based on your json strucutre you need class design like this
public class Rootobject
{
// do List<CurrencyDetail> if you are expecting multiple element
public CurrencyDetail btc_usd { get; set; }
public CurrencyDetail eth_usd { get; set; }
public CurrencyDetail doge_usd { get; set; }
public CurrencyDetail pac_usd { get; set; }
public CurrencyDetail rdd_usd { get; set; }
}
public class CurrencyDetail
{
public float high { get; set; }
public int low { get; set; }
public float avg { get; set; }
public float vol { get; set; }
public float vol_cur { get; set; }
public float last { get; set; }
public float buy { get; set; }
public float sell { get; set; }
public int updated { get; set; }
}
my suggesting is if possible modify you json , which will contain currency type in currency detail than you class strucutre will be like
public class Rootobject
{
public List<CurrencyDetail> currencies { get; set; }
}
public class CurrencyDetail
{
//btc_usd or eth_usd or doge_usd or pac_usd
public string type { get; set; }
public float high { get; set; }
public int low { get; set; }
public float avg { get; set; }
public float vol { get; set; }
public float vol_cur { get; set; }
public float last { get; set; }
public float buy { get; set; }
public float sell { get; set; }
public int updated { get; set; }
}

Extracting JSON data Xamarin

I am working a Xamarin.Forms App that uses the Azure Face API. With this API you retrieve a JSON response (See Below).
I want to extract the gender of the person in the image but am having trouble with it as I am very new to this.
I extract the full JSON response into a string but I would like to be able to extract data such as the 'Gender' or the 'Age' of the person in the image.
[{"faceId":"9448dfe4-afb6-4557-94fe-010fc439ff36","faceRectangle":{"top":635,"left":639,"width":789,"height":789},"faceAttributes":{"smile":0.187,"headPose":{"pitch":0.0,"roll":-1.6,"yaw":-7.9},"gender":"male","age":34.6,"facialHair":{"moustache":0.5,"beard":0.6,"sideburns":0.6},"glasses":"NoGlasses","emotion":{"anger":0.0,"contempt":0.69,"disgust":0.0,"fear":0.0,"happiness":0.187,"neutral":0.12,"sadness":0.002,"surprise":0.0},"blur":{"blurLevel":"low","value":0.15},"exposure":{"exposureLevel":"overExposure","value":0.85},"noise":{"noiseLevel":"medium","value":0.42},"makeup":{"eyeMakeup":false,"lipMakeup":false},"accessories":[],"occlusion":{"foreheadOccluded":false,"eyeOccluded":false,"mouthOccluded":false},"hair":{"bald":0.02,"invisible":false,"hairColor":[{"color":"brown","confidence":1.0},{"color":"black","confidence":0.95},{"color":"other","confidence":0.22},{"color":"blond","confidence":0.11},{"color":"gray","confidence":0.05},{"color":"red","confidence":0.04}]}}}]
This is how I set the JSON data to a string.
string contentString = await response.Content.ReadAsStringAsync();
You usually want to create a class that represents your response e. g. Person. Then you could use the Newtonsoft.Json nuget package to deserialize the object.:
var person = JsonConvert.DeserializeObject<Person>(contentString);
Now you can access the values like:
person.Gender
Using Newtonsoft.Json:
var results = JsonConvert.DeserializeObject<AzureFace>(contentString);
Debug.WriteLine(results.faceAttributes.age);
C# Model Used (via http://jsonutils.com)
public class FaceRectangle
{
public int top { get; set; }
public int left { get; set; }
public int width { get; set; }
public int height { get; set; }
}
public class HeadPose
{
public double pitch { get; set; }
public double roll { get; set; }
public double yaw { get; set; }
}
public class FacialHair
{
public double moustache { get; set; }
public double beard { get; set; }
public double sideburns { get; set; }
}
public class Emotion
{
public double anger { get; set; }
public double contempt { get; set; }
public double disgust { get; set; }
public double fear { get; set; }
public double happiness { get; set; }
public double neutral { get; set; }
public double sadness { get; set; }
public double surprise { get; set; }
}
public class Blur
{
public string blurLevel { get; set; }
public double value { get; set; }
}
public class Exposure
{
public string exposureLevel { get; set; }
public double value { get; set; }
}
public class Noise
{
public string noiseLevel { get; set; }
public double value { get; set; }
}
public class Makeup
{
public bool eyeMakeup { get; set; }
public bool lipMakeup { get; set; }
}
public class Occlusion
{
public bool foreheadOccluded { get; set; }
public bool eyeOccluded { get; set; }
public bool mouthOccluded { get; set; }
}
public class HairColor
{
public string color { get; set; }
public double confidence { get; set; }
}
public class Hair
{
public double bald { get; set; }
public bool invisible { get; set; }
public IList<HairColor> hairColor { get; set; }
}
public class FaceAttributes
{
public double smile { get; set; }
public HeadPose headPose { get; set; }
public string gender { get; set; }
public double age { get; set; }
public FacialHair facialHair { get; set; }
public string glasses { get; set; }
public Emotion emotion { get; set; }
public Blur blur { get; set; }
public Exposure exposure { get; set; }
public Noise noise { get; set; }
public Makeup makeup { get; set; }
public IList<object> accessories { get; set; }
public Occlusion occlusion { get; set; }
public Hair hair { get; set; }
}
public class AzureFace
{
public string faceId { get; set; }
public FaceRectangle faceRectangle { get; set; }
public FaceAttributes faceAttributes { get; set; }
}

Trouble parsing forecast.io weather data with Json.Net

I am relatively new to JSON and using an API forecast.io. It returns the JSON below, which I need to parse.
"daily":{
"summary":"Drizzle on Monday and Tuesday, with temperatures bottoming out at 91°F on Monday.","icon":"rain",
"data":[{
"time":1463770800,"summary":"Clear throughout the day.","icon":"clearday","sunriseTime":1463788956,"sunsetTime":1463839653,"moonPhase":0.48,"precipIntensity":0,"precipIntensityMax":0,"precipProbability":0,"temperatureMin":63.06,"temperatureMinTime":1463785200,"temperatureMax":95.23,"temperatureMaxTime":1463824800,"apparentTemperatureMin":63.06,"apparentTemperatureMinTime":1463785200,"apparentTemperatureMax":90.3,"apparentTemperatureMaxTime":1463824800,"dewPoint":37.34,"humidity":0.25,"windSpeed":3.44,"windBearing":22,"cloudCover":0,"pressure":1002.14,"ozone":283.7}
I extracted the "daily" portion successfully, but I could not get the "data" inside the "daily". I need to have the details, i.e. summary, time, icon, etc. I'd really appreciate some help.
Here is my C# code:
var test = new System.Net.WebClient().DownloadString("https://api.forecast.io/forecast/f2857958690caafc67d0dfba402c1f57/" + Latitude + "," + Longitude);
var json = JObject.Parse(test);
var daily = json.ToObject<DailyWeatherDTO>();
public class DailyWeatherDTO
{
public DailyWeatherData daily { get; set; }
}
public class DailyWeatherData
{
public daily data { get; set; }
}
public class daily
{
public string time { get; set; }
public String summary { get; set; }
public String icon { get; set; }
public String precipIntensity { get; set; }
public String precipProbability { get; set; }
public string sunriseTime { get; set; }
public string sunsetTime { get; set; }
public string moonPhase { get; set; }
public string precipIntensityMax { get; set; }
public string temperatureMin { get; set; }
public string temperatureMinTime { get; set; }
public string temperatureMax { get; set; }
public string temperatureMaxTime { get; set; }
public string apparentTemperatureMin { get; set; }
public string apparentTemperatureMinTime { get; set; }
public string apparentTemperatureMax { get; set; }
public string apparentTemperatureMaxTime { get; set; }
public string dewPoint { get; set; }
public string humidity { get; set; }
public string windSpeed { get; set; }
public string windBearing { get; set; }
public string cloudCover { get; set; }
public string pressure { get; set; }
public string ozone { get; set; }
}
First of all, the JSON you posted is not valid as shown. Specifically, you are missing a closing square bracket and curly brace at the end; plus, the whole thing needs to be enclosed in another pair of curly braces to be valid. Here is the corrected version, reformatted for readability:
{
"daily": {
"summary": "Drizzle on Monday and Tuesday, with temperatures bottoming out at 91°F on Monday.",
"icon": "rain",
"data": [
{
"time": 1463770800,
"summary": "Clear throughout the day.",
"icon": "clearday",
"sunriseTime": 1463788956,
"sunsetTime": 1463839653,
"moonPhase": 0.48,
"precipIntensity": 0,
"precipIntensityMax": 0,
"precipProbability": 0,
"temperatureMin": 63.06,
"temperatureMinTime": 1463785200,
"temperatureMax": 95.23,
"temperatureMaxTime": 1463824800,
"apparentTemperatureMin": 63.06,
"apparentTemperatureMinTime": 1463785200,
"apparentTemperatureMax": 90.3,
"apparentTemperatureMaxTime": 1463824800,
"dewPoint": 37.34,
"humidity": 0.25,
"windSpeed": 3.44,
"windBearing": 22,
"cloudCover": 0,
"pressure": 1002.14,
"ozone": 283.7
}
]
}
}
To be able to get all the data, your class structure needs to match the structure of the JSON. Assuming the above represents the complete JSON, here is what your classes should look like. In particular, notice the data property of the DailyWeatherData class is defined as a list of items (not a single object), which corresponds to the square brackets for the data property in the JSON.
public class DailyWeatherDTO // root-level container object
{
public DailyWeatherData daily { get; set; }
}
public class DailyWeatherData
{
public string summary { get; set; }
public string icon { get; set; }
public List<WeatherItem> data { get; set; }
}
public class WeatherItem
{
public int time { get; set; }
public string summary { get; set; }
public string icon { get; set; }
public int sunriseTime { get; set; }
public int sunsetTime { get; set; }
public double moonPhase { get; set; }
public int precipIntensity { get; set; }
public int precipIntensityMax { get; set; }
public int precipProbability { get; set; }
public double temperatureMin { get; set; }
public int temperatureMinTime { get; set; }
public double temperatureMax { get; set; }
public int temperatureMaxTime { get; set; }
public double apparentTemperatureMin { get; set; }
public int apparentTemperatureMinTime { get; set; }
public double apparentTemperatureMax { get; set; }
public int apparentTemperatureMaxTime { get; set; }
public double dewPoint { get; set; }
public double humidity { get; set; }
public double windSpeed { get; set; }
public int windBearing { get; set; }
public int cloudCover { get; set; }
public double pressure { get; set; }
public double ozone { get; set; }
}
With this class structure, you can deserialize the JSON like this:
DailyWeatherDTO dto = JsonConvert.DeserializeObject<DailyWeatherDTO>(json);
Here is a demo: https://dotnetfiddle.net/YTBrac

ServiceStack JsonServiceClient Silently Failing When Deserializing

I am working on an integration with the Expedia API. I am relatively new to ServiceStack but have managed pretty well so far, however, I've hit an issue with the deserialization of a JSON response from the API which seems to be failing despite having JsConfig.ThrowOnDeserializationError enabled.
JsConfig.Reset();
JsConfig.ThrowOnDeserializationError = true;
var availability = _client.Get<ExpediaHotelRoomAvailability>("avail?" + querystring);
In order to see the API response I am working with please use the following request:
GET http://dev.api.ean.com/ean-services/rs/hotel/v3/avail?minorRev=26&cid=55505&apiKey=cbrzfta369qwyrm9t5b8y8kf&customerUserAgent=Mozilla%2f5.0+(Windows+NT+6.3%3b+WOW64)+AppleWebKit%2f537.36+(KHTML%2c+like+Gecko)+Chrome%2f35.0.1916.114+Safari%2f537.36&customerIpAddress=%3a%3a1&hotelId=135857&arrivalDate=06%2f07%2f2014&departureDate=06%2f20%2f2014&includeDetails=true&includeRoomImages=true&room1=2 HTTP/1.1
User-Agent: Fiddler
Content-Type: text/json
Host: dev.api.ean.com
Here is a typical response:
{
"HotelRoomAvailabilityResponse":{
"#size":"1",
"customerSessionId":"0ABAAA7A-D42E-2914-64D2-01C0F09040D8",
"hotelId":135857,
"arrivalDate":"06\/07\/2014",
"departureDate":"06\/20\/2014",
"hotelName":"La Quinta Inn and Suites Raleigh Cary",
"hotelAddress":"191 Crescent Commons",
"hotelCity":"Cary",
"hotelStateProvince":"NC",
"hotelCountry":"US",
"numberOfRoomsRequested":1,
"checkInInstructions":"",
"tripAdvisorRating":4.5,
"tripAdvisorReviewCount":189,
"tripAdvisorRatingUrl":"http:\/\/www.tripadvisor.com\/img\/cdsi\/img2\/ratings\/traveler\/4.5-12345-4.gif",
"HotelRoomResponse":{
"rateCode":14587,
"roomTypeCode":14587,
"rateDescription":"Standard Room, 1 King Bed",
"roomTypeDescription":"Standard Room, 1 King Bed",
"supplierType":"E",
"propertyId":67977,
"BedTypes":{
"#size":"1",
"BedType":{
"#id":"14",
"description":"1 king"
}
},
"smokingPreferences":"S,NS",
"rateOccupancyPerRoom":3,
"quotedOccupancy":2,
"minGuestAge":0,
"RateInfos":{
"#size":"1",
"RateInfo":{
"#priceBreakdown":"true",
"#promo":"false",
"#rateChange":"true",
"RoomGroup":{
"Room":{
"numberOfAdults":2,
"numberOfChildren":0,
"rateKey":"0214364d-6819-4631-aa97-a162c43e0297"
}
},
"ChargeableRateInfo":{
"#averageBaseRate":"109.61539",
"#averageRate":"109.61539",
"#commissionableUsdTotal":"1425.0",
"#currencyCode":"USD",
"#maxNightlyRate":"165.0",
"#nightlyRateTotal":"1425.0",
"#surchargeTotal":"229.19",
"#total":"1654.19",
"NightlyRatesPerRoom":{
"#size":"13",
"NightlyRate":[
{
"#baseRate":"90.0",
"#rate":"90.0",
"#promo":"false"
},
{
"#baseRate":"90.0",
"#rate":"90.0",
"#promo":"false"
},
{
"#baseRate":"100.0",
"#rate":"100.0",
"#promo":"false"
},
{
"#baseRate":"115.0",
"#rate":"115.0",
"#promo":"false"
},
{
"#baseRate":"115.0",
"#rate":"115.0",
"#promo":"false"
},
{
"#baseRate":"115.0",
"#rate":"115.0",
"#promo":"false"
},
{
"#baseRate":"165.0",
"#rate":"165.0",
"#promo":"false"
},
{
"#baseRate":"165.0",
"#rate":"165.0",
"#promo":"false"
},
{
"#baseRate":"90.0",
"#rate":"90.0",
"#promo":"false"
},
{
"#baseRate":"95.0",
"#rate":"95.0",
"#promo":"false"
},
{
"#baseRate":"95.0",
"#rate":"95.0",
"#promo":"false"
},
{
"#baseRate":"95.0",
"#rate":"95.0",
"#promo":"false"
},
{
"#baseRate":"95.0",
"#rate":"95.0",
"#promo":"false"
}
]
},
"Surcharges":{
"#size":"1",
"Surcharge":{
"#type":"TaxAndServiceFee",
"#amount":"229.19"
}
}
},
"cancellationPolicy":"We understand that sometimes your travel plans change. We do not charge a change or cancel fee. However, this property (La Quinta Inn and Suites Raleigh Cary) imposes the following penalty to its customers that we are required to pass on: Cancellations or changes made after 6:00 PM ((GMT-05:00) Eastern Time (US & Canada)) on Jun 6, 2014 are subject to a 1 Night Room & Tax penalty. The property makes no refunds for no shows or early checkouts.",
"CancelPolicyInfoList":{
"CancelPolicyInfo":[
{
"versionId":208699803,
"cancelTime":"18:00:00",
"startWindowHours":0,
"nightCount":1,
"currencyCode":"USD",
"timeZoneDescription":"(GMT-05:00) Eastern Time (US & Canada)"
},
{
"versionId":208778550,
"cancelTime":"18:00:00",
"startWindowHours":24,
"nightCount":0,
"currencyCode":"USD",
"timeZoneDescription":"(GMT-05:00) Eastern Time (US & Canada)"
}
]
},
"nonRefundable":false,
"rateType":"MerchantStandard",
"currentAllotment":0,
"guaranteeRequired":false,
"depositRequired":true,
"taxRate":229.19
}
},
"ValueAdds":{
"#size":"3",
"ValueAdd":[
{
"#id":"2048",
"description":"Free Wireless Internet"
},
{
"#id":"2",
"description":"Continental Breakfast"
},
{
"#id":"128",
"description":"Free Parking"
}
]
},
"deepLink":"https:\/\/travel.ian.com\/templates\/55505\/hotels\/135857\/book?lang=en&standardCheckin=06\/07\/2014&standardCheckout=06\/20\/2014&selectedPrice=1654.190000&supplierType=E&rateCode=14587&roomTypeCode=14587&roomsCount=1&rooms[0].adultsCount=2&rateKey=0214364d-6819-4631-aa97-a162c43e0297",
"RoomImages":{
"#size":"1",
"RoomImage":{
"url":"http:\/\/media.expedia.com\/hotels\/1000000\/70000\/68000\/67977\/67977_103_s.jpg"
}
}
}
}
}
A large part of the response is de-serialized fine except for all of the rate information which I am really interested in. No exceptions are thrown during the deserialization so I have little to go on in terms of tracking down the exact problem. To be more specific let's take the ChargeableRateInfo - all values contained within are either null or zero.
Here is my class I am trying to deserialize the response to:
namespace MyCustomNamespace
{
using System.Collections.Generic;
public class BedType
{
public string description { get; set; }
public string id { get; set; }
}
public class BedTypes
{
public BedType BedType { get; set; }
public int size { get; set; }
}
public class Room
{
public int numberOfAdults { get; set; }
public int numberOfChildren { get; set; }
public string rateKey { get; set; }
}
public class RoomGroup
{
public Room Room { get; set; }
}
public class NightlyRate
{
public string baseRate { get; set; }
public string promo { get; set; }
public string rate { get; set; }
}
public class NightlyRatesPerRoom
{
public List<NightlyRate> NightlyRate { get; set; }
public int size { get; set; }
}
public class Surcharge
{
public decimal amount { get; set; }
public string type { get; set; }
}
public class Surcharges
{
public Surcharge Surcharge { get; set; }
public int size { get; set; }
}
public class ChargeableRateInfo
{
public NightlyRatesPerRoom NightlyRatesPerRoom { get; set; }
public Surcharges Surcharges { get; set; }
public decimal averageBaseRate { get; set; }
public decimal averageRate { get; set; }
public decimal commissionableUsdTotal { get; set; }
public string currencyCode { get; set; }
public decimal maxNightlyRate { get; set; }
public decimal nightlyRateTotal { get; set; }
public decimal surchargeTotal { get; set; }
public decimal total { get; set; }
}
public class CancelPolicyInfo
{
public string cancelTime { get; set; }
public string currencyCode { get; set; }
public int nightCount { get; set; }
public int percent { get; set; }
public int startWindowHours { get; set; }
public string timeZoneDescription { get; set; }
public int versionId { get; set; }
}
public class CancelPolicyInfoList
{
public List<CancelPolicyInfo> CancelPolicyInfo { get; set; }
}
public class RateInfo
{
public CancelPolicyInfoList CancelPolicyInfoList { get; set; }
public ChargeableRateInfo ChargeableRateInfo { get; set; }
public RoomGroup RoomGroup { get; set; }
public string cancellationPolicy { get; set; }
public int currentAllotment { get; set; }
public bool depositRequired { get; set; }
public bool guaranteeRequired { get; set; }
public bool nonRefundable { get; set; }
public string priceBreakdown { get; set; }
public string promo { get; set; }
public string promoType { get; set; }
public string rateChange { get; set; }
public string rateType { get; set; }
public decimal taxRate { get; set; }
}
public class RateInfos
{
public RateInfo RateInfo { get; set; }
public int size { get; set; }
}
public class ValueAdd
{
public string description { get; set; }
public string id { get; set; }
}
public class ValueAdds
{
public List<ValueAdd> ValueAdd { get; set; }
public int size { get; set; }
}
public class RoomImage
{
public string url { get; set; }
}
public class RoomImages
{
public RoomImage RoomImage { get; set; }
public int size { get; set; }
}
public class HotelRoomResponse
{
public BedTypes BedTypes { get; set; }
public RateInfos RateInfos { get; set; }
public RoomImages RoomImages { get; set; }
public ValueAdds ValueAdds { get; set; }
public string deepLink { get; set; }
public int minGuestAge { get; set; }
public int propertyId { get; set; }
public int quotedOccupancy { get; set; }
public int rateCode { get; set; }
public string rateDescription { get; set; }
public int rateOccupancyPerRoom { get; set; }
public int roomTypeCode { get; set; }
public string roomTypeDescription { get; set; }
public string smokingPreferences { get; set; }
public string supplierType { get; set; }
}
public class HotelRoomAvailabilityResponse
{
public List<HotelRoomResponse> HotelRoomResponse { get; set; }
public string arrivalDate { get; set; }
public string checkInInstructions { get; set; }
public string customerSessionId { get; set; }
public string departureDate { get; set; }
public string hotelAddress { get; set; }
public string hotelCity { get; set; }
public string hotelCountry { get; set; }
public int hotelId { get; set; }
public string hotelName { get; set; }
public string hotelStateProvince { get; set; }
public int numberOfRoomsRequested { get; set; }
public int size { get; set; }
public decimal tripAdvisorRating { get; set; }
public string tripAdvisorRatingUrl { get; set; }
public int tripAdvisorReviewCount { get; set; }
}
public class ExpediaHotelRoomAvailability
{
public HotelRoomAvailabilityResponse HotelRoomAvailabilityResponse { get; set; }
}
}
Could this possibly have something to do with the # symbols in the JSON and if so how do I get around this?
You can handle the # symbols named fields by providing their name using a [DataMember(Name=...)] attribute.
Unfortunately this mean you have to provide a [DataContract] attribute on your DTO, which means all the properties then become opt-in. So all properties will need to have [DataMember] to be included, which makes the DTO less readable.
So your NightlyRate DTO becomes:
[DataContract]
public class NightlyRate
{
[DataMember(Name="#baseRate")]
public string baseRate { get; set; }
[DataMember(Name="#promo")]
public string promo { get; set; }
[DataMember(Name="#rate")]
public string rate { get; set; }
}
And NightlyRatesPerRoom would be:
[DataContract]
public class NightlyRatesPerRoom
{
[DataMember]
public List<NightlyRate> NightlyRate { get; set; }
[DataMember(Name="#size")]
public int size { get; set; }
}
Obviously you will have to mark up the other DTOs as appropriate. I hope that helps.

Categories