我目前在REST api中使用dotnet核心有一个关于async / await的问题。我正在开发一个api,它需要使用来自HttpClient的GetAsync方法进行一些http调用。以下是它的工作原理:
这是我的get方法进入我的控制器:
[HttpGet]
public async Task<IActionResult> Get(string url, string aid)
{
try
{
//...
var cancellationTokenSource = new CancellationTokenSource();
var task = Task.Factory.StartNew(async () => await _htmlService.HtmlLinkCheck(aid, cancellationTokenSource.Token, correctUrl), cancellationTokenSource.Token);
ConnectionsHelper.RegisterTask(aid, task, cancellationTokenSource);
ConnectionsHelper.UpRequest(aid);
return Ok("Ok");
}
catch (Exception exception)
{
return this.InternalServerError(exception);
}
}
此方法正在调用在启动文件中注入和配置的服务,如下所示:
services.AddScoped<IRequestService, RequestService>();
services.AddScoped<IHtmlCheckService, HtmlCheckService>();
进入HtmlLinkCheck进入HtmlLinkCheck我正在调用requestService进行调用:
private async Task CheckHtmlLink(CancellationToken token)
{
//...
var result = await _requestService.GetRequest(handledUrl.url);
和GetRequest方法执行:
public async Task<string> GetRequest(Uri url)
{
// ...
var response = await _httpClient.GetAsync(url);
_httpClient是一个静态变量(由RequestService的所有不同实例使用):
private static HttpClient _httpClient;
public RequestService()
{
var handler = new HttpClientHandler();
if (handler.SupportsAutomaticDecompression)
{
handler.AutomaticDecompression = DecompressionMethods.GZip |
DecompressionMethods.Deflate;
}
_httpClient = new HttpClient(handler);
_httpClient.DefaultRequestHeaders.Add("User-Agent", "Mozilla/5.0 (Windows NT 10.0; WOW64; rv:51.0) Gecko/20100101 Firefox/51.0");
}
如果我的im让我们向我的REST API发出100个请求,那么对于每个请求,对每个请求之间的GetAsync调用将是线程安全的(不是一次调用,而是并行调用) RequestService因为AddScope方法创建注入)?它看起来好像是并行工作,但我怎么能确定它呢?
为每个RequestService实例创建一个新的httpClient实例会更有效吗?
提前感谢您的回答
答案 0 :(得分:2)
HttpClient
旨在允许多个同时请求。
使用后,您无法更改{em>属性,如BaseAddress
或DefaultRequestHeaders
;如果您需要为不同的请求设置不同的属性,那么您应该为这些请求使用不同的HttpClient
实例。
但是在一般情况下,是的,您应该为每个共享其属性值的请求使用一个HttpClient
实例。