imsan
imsan

Reputation: 449

Reuse httpClient created via the HttpClientFactory in different methods of the same class? (C# / .NET)

I have a class into which the IHttpClientFactory is injected via the constructor. There's also a HttpClient private field in this class.

Are there any issues with creating the HttpClient in the constructor, using the factory, and then reusing that HttpClient in two/multiple methods within that one class to make two/multiple different api calls? (Same Api, different endpoints)

Or would it be better to use the factory in each method to create a new client. What are the implications/pros & cons of each approach? Is any one inherently better or doesn't it matter?

private readonly HttpClient _httpClient;

public RestClient(IHttpClientFactory httpClientFactory)
{
   _httpClient = httpClientFactory.CreateClient();
}

public async Task<SomeResponse> Method1(SomeRequest request)
{
    ...

        using (var httpRequestMessage = new HttpRequestMessage(HttpMethod.Post, url))
        {
             httpRequestMessage.Headers.Add("Accept", "application/json");
                    httpRequestMessage.Headers.Add("Authorization", "Basic " + credentials);
                    httpRequestMessage.Content = new StringContent(jsonBody, Encoding.UTF8, "application/json");

            using (var response = await _httpClient.SendAsync(httpRequestMessage))
            {
                ...
            }
        }
...
}

public async Task<SomeOtherResponse> Method2(someInput)
{
   ...

        using (var httpRequestMessage = new HttpRequestMessage(HttpMethod.Get, uri.ToString()))
        {
            httpRequestMessage.Headers.Add("Accept", "image/png");
            httpRequestMessage.Headers.Add("Authorization", "Basic " + credentials);

            using (var response = await _httpClient.SendAsync(httpRequestMessage))
            {
                ...
            }
        }
...
}


Edit: have looked at this post Should I cache and reuse HttpClient created from HttpClientFactory? but it doesn't answer my questions. If there is something to be derived from there please explain.

Upvotes: 3

Views: 4637

Answers (1)

Peter Csala
Peter Csala

Reputation: 22819

I think you are looking for this guidance from Microsoft: Guidelines for using HttpClient

I copy here the related part

Recommended use

In .NET Core and .NET 5+:

Use a static or singleton HttpClient instance with PooledConnectionLifetime set to the desired interval, such as two minutes, depending on expected DNS changes. This solves both the socket exhaustion and DNS changes problems without adding the overhead of IHttpClientFactory. If you need to be able to mock your handler, you can register it separately.

Using IHttpClientFactory, you can have multiple, differently configured clients for different use cases. However, be aware that the factory-created clients are intended to be short-lived, and once the client is created, the factory no longer has control over it.

The factory pools HttpMessageHandler instances, and, if its lifetime hasn't expired, a handler can be reused from the pool when the factory creates a new HttpClient instance. This reuse avoids any socket exhaustion issues.

If you desire the configurability that IHttpClientFactory provides, we recommend using the typed-client approach.

In .NET Framework:

Use IHttpClientFactory to manage your HttpClient instances. If you create a new client instance for each request, you can exhaust available sockets.

Tip

If your app requires cookies, consider disabling automatic cookie handling or avoiding IHttpClientFactory. Pooling the HttpMessageHandler instances results in sharing of CookieContainer objects. Unanticipated CookieContainer object sharing often results in incorrect code.

Upvotes: 1

Related Questions