HttpClient inject into Singleton



假设我们有这样的代码:

services.AddHttpClient();
services.AddSingleton<IMyService, MyService>();
...
public class MyService : IMyService
{
public MyService(HttpClient httpClient)
{
}
}

有一些问题(可能很愚蠢,但我只想澄清一些事情(:

  1. 它会使用HttpClientFactory来创建HttpClient的实例吗
  2. 我猜它使用HttpClientFactory,但在这种情况下,它会在DNS更改方面出现问题吗

目前还不太清楚HttpMessageHandler是否会针对单例服务进行管理,并且是否应该对服务进行作用域划分,以获得HttpClientFactory使用的所有好处。

  1. 它会使用HttpClientFactory创建HttpClient的实例吗

是。在HttpClientFactory注册期间,默认HttpClient被注册为临时服务。

  1. 我猜它使用HttpClientFactory,但在这种情况下,它会在DNS更改方面出现问题吗

正确,它仍然会。当您将它注入到单例中时,这里的HttpClient将只创建一次。为了利用HttpClientFactoryHttpMessageHandler池,您需要HttpClient是短命的。因此,为此,您需要注入IHttpClientFactory本身,并在需要时调用CreateClient。(请注意,短寿命HttpClient仅适用于HttpClientFactory的使用(。BTW切换到类型化客户端在注入单例时没有帮助,HttpClient最终仍然只创建一次,请参阅https://github.com/dotnet/runtime/issues/64034.

此外,您实际上可以完全避免HttpClientFactory,并且仍然可以尊重DNS更改。为此,您可能有一个静态/单例HttpClient,其中PooledConnectionLifetime设置为某个合理的超时(例如HttpClientFactory所做的相同的2分钟(

services.AddSingleton(() => new HttpClient(
new SocketsHttpHandler { PooledConnectionLifetime = TimeSpan.FromMinutes(2) }
));