使用.NET 4.0任务模式将JSON反序列化为使用HTTPClient .ReadAsAsync的数组或列表
我试图反序列化从http://api.usa.gov/jobs/search.json?query=nursing+jobs使用.NET 4.0任务模式返回的JSON。 它返回这个JSON('加载JSON数据'@ http://jsonviewer.stack.hu/ )。 
 [ { "id": "usajobs:353400300", "position_title": "Nurse", "organization_name": "Indian Health Service", "rate_interval_code": "PA", "minimum": 42492, "maximum": 61171, "start_date": "2013-10-01", "end_date": "2014-09-30", "locations": [ "Gallup, NM" ], "url": "https://www.usajobs.gov/GetJob/ViewDetails/353400300" }, { "id": "usajobs:359509200", "position_title": "Nurse", "organization_name": "Indian Health Service", "rate_interval_code": "PA", "minimum": 42913, "maximum": 61775, "start_date": "2014-01-16", "end_date": "2014-12-31", "locations": [ "Gallup, NM" ], "url": "https://www.usajobs.gov/GetJob/ViewDetails/359509200" }, ... ] 
索引操作:
  public class HomeController : Controller { public ActionResult Index() { Jobs model = null; var client = new HttpClient(); var task = client.GetAsync("http://api.usa.gov/jobs/search.json?query=nursing+jobs") .ContinueWith((taskwithresponse) => { var response = taskwithresponse.Result; var jsonTask = response.Content.ReadAsAsync<Jobs>(); jsonTask.Wait(); model = jsonTask.Result; }); task.Wait(); ... } 
工作和工作类:
  [JsonArray] public class Jobs { public List<Job> JSON; } public class Job { [JsonProperty("organization_name")] public string Organization { get; set; } [JsonProperty("position_title")] public string Title { get; set; } } 
 当我设置jsonTask.Wait(); 并检查jsonTask的状态是jsonTask 。  InnerException是“typesProjectName.Jobs不是集合”。 
我开始与乔布斯types没有JsonArray属性和作为一个数组(作业[]),并得到了这个错误。
  public class Jobs { public Job[] JSON; } + InnerException {"Cannot deserialize the current JSON array (eg [1,2,3]) into type 'ProjectName.Models.Jobs' because the type requires a JSON object (eg {\"name\":\"value\"}) to deserialize correctly.\r\n To fix this error either change the JSON to a JSON object (eg {\"name\":\"value\"}) or change the deserialized type to an array or a type that implements a collection interface (eg ICollection, IList) like List<T> that can be deserialized from a JSON array. JsonArrayAttribute can also be added to the type to force it to deserialize from a JSON array.\r\n Path '', line 1, position 1."} System.Exception {Newtonsoft.Json.JsonSerializationException} 
 如何处理这个网站的JSON与.NET 4.0任务模式? 我想在.NET 4.5中await async到await async模式之前,先完成这个工作。 
答案更新:
下面是一个使用brumScouse的答案使用.NET 4.5asynchronous等待模式的示例。
  public async Task<ActionResult>Index() { List<Job> model = null; var client = newHttpClient(); // .NET 4.5 async await pattern var task = await client.GetAsync(http://api.usa.gov/jobs/search.json?query=nursing+jobs); var jsonString = await task.Content.ReadAsStringAsync(); model = JsonConvert.DeserializeObject<List<Job>>(jsonString); returnView(model); } 
 您将需要引入System.Threading.Tasks命名空间。 
  注意:在.ReadAsString上没有.ReadAsString方法,这就是我使用.ReadAsStringAsync方法的原因。 
不要手动模型尝试使用像Json2csharp.com网站的东西。 粘贴在一个示例JSON响应中,越完善,然后拉入生成的生成的类。 这至less会带走一些运动的部件,会让你在csharp中获得JSON的形状,给串行器更容易的时间,而且你不需要添加属性。
只要让它工作,然后修改你的类名称,以符合你的命名约定,并在稍后添加属性。
编辑:好了后,有点搞乱我已经成功地将结果反序列化到作业列表(我用Json2csharp.com为我创build类)
 public class Job { public string id { get; set; } public string position_title { get; set; } public string organization_name { get; set; } public string rate_interval_code { get; set; } public int minimum { get; set; } public int maximum { get; set; } public string start_date { get; set; } public string end_date { get; set; } public List<string> locations { get; set; } public string url { get; set; } } 
并编辑你的代码:
  List<Job> model = null; var client = new HttpClient(); var task = client.GetAsync("http://api.usa.gov/jobs/search.json?query=nursing+jobs") .ContinueWith((taskwithresponse) => { var response = taskwithresponse.Result; var jsonString = response.Content.ReadAsStringAsync(); jsonString.Wait(); model = JsonConvert.DeserializeObject<List<Job>>(jsonString.Result); }); task.Wait(); 
这意味着你可以摆脱你的包含对象。 值得注意的是,这不是一个与任务有关的问题,而是一个反序列化问题。
编辑2:
有一种方法可以获取JSON对象并在Visual Studio中生成类。 只需复制select的JSON,然后编辑>select性粘贴>将JSON粘贴为类。 整个页面专门在这里:
http://blog.codeinside.eu/2014/09/08/Visual-Studio-2013-Paste-Special-JSON-And-Xml/
 var response = taskwithresponse.Result; var jsonString = response.ReadAsAsync<List<Job>>().Result; 
返回types取决于服务器,有时响应确实是一个JSON数组,但是以text / plain方式发送
在请求中设置接受标题应该得到正确的types:
 client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json")); 
然后可以将其序列化为JSON列表或数组。 感谢@svick的评论,这让我好奇它应该工作。
我没有configuration接受头的exception是System.Net.Http.UnsupportedMediaTypeException。
下面的代码更清洁,应该工作(未经testing,但在我的情况下):
  var client = new HttpClient(); client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json")); var response = await client.GetAsync("http://api.usa.gov/jobs/search.json?query=nursing+jobs"); var model = response.Content.ReadAsAsync<List<Job>>();