在ASP.NET Core中应用HttpClient获取数据和内容(2)

private readonly JsonSerializerOptions _options; public HttpClientCrudService() { _httpClient.BaseAddress = new Uri("https://localhost:5001/api/"); _httpClient.Timeout = new TimeSpan(0, 0, 30); _options = new JsonSerializerOptions { PropertyNameCaseInsensitive = true }; } public async Task Execute() { await GetCompanies(); }

我们为JsonSerializer配置不区分巨细写的反序列化选项。没有它,我们的响应就不会被正确地反序列化。

此刻,我们可以在GetCompanies要领中添加一个断点,启动Web API项目,然后启动客户端:

在ASP.NET Core中应用HttpClient获取数据和内容

正如我们所看到的,我们在companies变量中获得了功效。

支持差异的响应名目

在本例中,我们吸收到一个JSON作为默认的响应名目。我们的API默认支持这种范例。但有些API不默认为JSON,它们大概支持XML作为默认的响应名目或任何其他名目。在这种环境下,我们的逻辑就行不通了。

除了JSON之外,我们的API还支持XML响应名目。让我们看看如安在客户端应用措施中明晰地要求名目。

首先,Http请求和响应都包括一组头,我们可以利用这些头在客户端和处事器应用措施之间通报附加信息。HTTP请求的通用头是Accept。我们利用这个头汇报处事器客户端将接管哪种媒体范例:accept: application/json, text/xml。

所以,让我们看看如安在我们的请求中配置头:

public HttpClientCrudService() { _httpClient.BaseAddress = new Uri("https://localhost:5001/api/"); _httpClient.Timeout = new TimeSpan(0, 0, 30); _httpClient.DefaultRequestHeaders.Clear(); _httpClient.DefaultRequestHeaders.Accept.Add( new MediaTypeWithQualityHeaderValue("application/json")); _httpClient.DefaultRequestHeaders.Accept.Add( new MediaTypeWithQualityHeaderValue("text/xml")); _options = new JsonSerializerOptions { PropertyNameCaseInsensitive = true }; }

这里,我们利用DefaultRequestHeaders属性并将其排除。然后,我们利用Accept属性,由于它是一个荟萃,所以我们添加了两个MediaTypeWithQualityHeaderValue工具。对付第一个工具,我们支持JSON名目,对付第二个工具,我们支持XML名目。为此,我们需要添加一个新的using语句:

using System.Net.Http.Headers;

此刻,假如有一个像这样的设置,必需在要领中添加一些特另外代码,以抉择如何反序列化响应:

public async Task GetCompanies() { var response = await _httpClient.GetAsync("companies"); response.EnsureSuccessStatusCode(); var content = await response.Content.ReadAsStringAsync(); var companies = new List<CompanyDto>(); if(response.Content.Headers.ContentType.MediaType == "application/json") { companies = JsonSerializer.Deserialize<List<CompanyDto>>(content, _options); } else if(response.Content.Headers.ContentType.MediaType == "text/xml") { var doc = XDocument.Parse(content); foreach (var element in doc.Descendants()) { element.Attributes().Where(a => a.IsNamespaceDeclaration).Remove(); element.Name = element.Name.LocalName; } var serializer = new XmlSerializer(typeof(List<CompanyDto>)); companies = (List<CompanyDto>)serializer.Deserialize(new StringReader(doc.ToString())); } }

由于我们同时支持JSON和XML名目,我们必需查抄哪个ContentType被应用到响应。假如是JSON,我们只需执行尺度的反序列化。但假如是XML,我们将内容理会为XDocument。最后,我们建设一个新的XmlSerializer并反序列化XDocument。

此时,假如我们启动两个应用措施,并在要领中安排一个断点,我们将看到我们的默认名目是JSON:

在ASP.NET Core中应用HttpClient获取数据和内容

HttpClient中的优先级

在我们的Accept头配置中,我们支持两种具有沟通优先级的名目。优先级的最大值为1。可是,我们可觉得这两个头文件中的一个配置较低的首选项——值必需在0到1之间。有较高值的请求将有更高优先级。

所以,让我们在结构函数中低落JSON Accept头的优先级:

_httpClient.DefaultRequestHeaders.Clear(); _httpClient.DefaultRequestHeaders.Accept.Add( new MediaTypeWithQualityHeaderValue("application/json", 0.9)); _httpClient.DefaultRequestHeaders.Accept.Add( new MediaTypeWithQualityHeaderValue("text/xml"));

正如我们所看到的,MediaTypeWithQualityHeaderValue结构函数接管另一个参数。我们将它的值配置为0.9。因为我们没有为XML Accept头添加任何值,所以默认值是1。此刻,假如我们开始我们的应用措施,我们会发明XML是优先级更高的名目:

在ASP.NET Core中应用HttpClient获取数据和内容

因此,执行将跳过这一部门并执行我们的XML反序列化。让我们在XDocument理会之前查抄响应体:

在ASP.NET Core中应用HttpClient获取数据和内容

然后,让我们在理会操纵之后查抄doc变量:

在ASP.NET Core中应用HttpClient获取数据和内容

我们可以看出区别。在理会操纵之后,反序列化就乐成完成了:

在ASP.NET Core中应用HttpClient获取数据和内容

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/wsjfyj.html