从标准为单例 httpclient
的代码重构到新的 ihttpfactory
我对 httpClient
的生命周期感到非常困惑:
类型化客户端在 DI 中注册为 transient 。
[Typed clients]
这意味着我之前依赖于 httpclient
的所有单例服务现在都将效仿 [即是短暂的]。我找不到关于此设计选择的支持文档?现在这不会对性能造成伤害,因为我们必须使所有依赖关系图都成为 transient 的吗?
最佳答案
Google“键入的httpclient transient”是你的 friend :https://www.stevejgordon.co.uk/ihttpclientfactory-patterns-using-typed-clients-from-singleton-services
简单地说,不是直接注入(inject)和使用类型化 HttpClient,而是创建一个依赖于 IServiceProvider 的工厂,使用该服务提供者返回类型化 HttpClient 实例的方法,然后注入(inject)该工厂。然后每次需要类型化 HttpClient 的实例时调用工厂的创建方法。服务提供商为您进行所有范围管理。
换句话说,不是以下内容:
services.AddHttpClient<IMyHttpClient, MyHttpClient>();
services.AddScoped<IDependsOnHttpClient, DependsOnHttpClient>();
...
public class DependsOnHttpClient : IDependsOnHttpClient
{
private readonly IMyHttpClient _httpClient;
public DependsOnHttpClient(IMyHttpClient httpClient)
=> _httpClient = httpClient;
public async Task DoSomethingWithHttpClientAsync()
=> _httpClient.GetAsync("https://foo.bar");
}
你写:
services.AddHttpClient<IMyHttpClient, MyHttpClient>();
services.AddSingleton<IMyHttpClientFactory, MyHttpClientFactory>();
services.AddSingleton<IDependsOnHttpClient, DependsOnHttpClient>();
...
public class MyHttpClientFactory : IMyHttpClientFactory
{
private readonly IServiceProvider _serviceProvider;
public MyHttpClientFactory(IServiceProvider serviceProvider)
=> _serviceProvider = serviceProvider;
public IMyHttpClient CreateClient()
=> _serviceProvider.GetRequiredService<IMyHttpClient>();
}
public class DependsOnHttpClient : IDependsOnHttpClient
{
private readonly IMyHttpClientFactory _httpClientFactory;
public DependsOnHttpClient(IMyHttpClientFactory httpClientFactory)
=> _httpClientFactory = httpClientFactory;
public async Task DoSomethingWithHttpClientAsync()
{
var httpClient = _httpClientFactory.CreateClient();
return await _httpClient.GetAsync("https://foo.bar");
}
}
此时您可能想知道“通过编写所有这些代码与仅注入(inject) IHttpClientFactory 并调用其方法相比,我能获得什么”,老实说,我不确定答案。也许使用 Roslyn 源代码生成器,我们将能够为它们生成类型化的 HttpClient 和工厂。
关于c# - 对新 ihttpfactory 中 httpclient 的生命周期感到困惑,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/68909241/