状态代码不成功时无法读取 HttpResponseMessage 内容



我有一个服务正在使用HttpClient来消耗短信 REST API:

HttpClient http = this._httpClientFactory.CreateClient();
// Skipped: setup HttpRequestMessage
using (HttpResponseMessage response = await http.SendAsync(request))
{
try
{
_ = response.EnsureSuccessStatusCode();
}
catch (HttpRequestException)
{
string responseString = await response.Content.ReadAsStringAsync(); // Fails with ObjectDisposedException
this._logger.LogInformation(
"Received invalid HTTP response status '{0}' from SMS API. Response content was {1}.",
(int)response.StatusCode,
responseString
);
throw;
}
}

API 返回错误,但我希望能够记录它。所以我需要记录失败状态代码(我可以从response.StatusCode中读取(和相关内容(可能包含其他错误有用的详细信息(。

此代码在指令await response.Content.ReadAsStringAsync()上失败,但以下异常:

System.ObjectDisposedException:无法访问已释放的对象。
对象名称:"System.Net.Http.HttpConnection+HttpConnectionResponseContent"。
    模块 "System.Net.Http.HttpContent", in checkDispose
    Module "System.Net.Http.HttpContent", in ReadAsStringAsync

一些来源建议,当状态代码不在成功范围 (200-299( 内时,不应阅读响应内容,但如果响应确实包含有用的错误详细信息怎么办?

使用的.NET版本:AWS lambda linux运行时上的.NET Core 2.1.12。

好的,显然这是 .NET API 中的一个已知问题,已在 .NET Core 3.0 中得到解决。response.EnsureSuccessStatusCode()实际上是在处理响应内容。它以这种方式实现,据说可以帮助用户:

处理内容应该对用户有帮助:如果用户调用 EnsureSuccessStatusCode((,
如果响应状态代码为 != 2xx,则抛出异常//即行为类似于失败的请求(例如/
/连接失败(。在这种情况下,用户不希望释放内容:如果抛出异常
//,则对象负责清理其状态。

这是从 3.0 中删除的不良行为。同时,我只是在日志之前切换到使用IsSuccessStatusCode

HttpClient http = this._httpClientFactory.CreateClient();
// Skipped: setup HttpRequestMessage
using (HttpResponseMessage response = await http.SendAsync(request))
{
if (!response.IsSuccessStatusCode)
{
string responseString = await response.Content.ReadAsStringAsync(); // Fails with ObjectDisposedException
this._logger.LogInformation(
"Received invalid HTTP response status '{0}' from SMS API. Response content was {1}.",
(int)response.StatusCode,
responseString
);
_ = response.EnsureSuccessStatusCode();
}
}

有点多余,但它应该有效。

最新更新