Do Httpclient and Httpclienthandler Have to Be Disposed Between Requests

Do HttpClient and HttpClientHandler have to be disposed between requests?

The general consensus is that you do not (should not) need to dispose of HttpClient.

Many people who are intimately involved in the way it works have stated this.

See Darrel Miller's blog post and a related SO post: HttpClient crawling results in memory leak for reference.

I'd also strongly suggest that you read the HttpClient chapter from Designing Evolvable Web APIs with ASP.NET for context on what is going on under the hood, particularly the "Lifecycle" section quoted here:

Although HttpClient does indirectly implement the IDisposable
interface, the standard usage of HttpClient is not to dispose of it
after every request. The HttpClient object is intended to live for as
long as your application needs to make HTTP requests. Having an object
exist across multiple requests enables a place for setting
DefaultRequestHeaders and prevents you from having to re-specify
things like CredentialCache and CookieContainer on every request as
was necessary with HttpWebRequest.

Or even open up DotPeek.

Do Windows.Web.Http.HttpClient have to be disposed per HTTP request?

It seems to me that if it were intended to be used for only one request at a time, it would simply throw an exception if you tried to use it for more than one.

Also, consider that all but the earliest version of HTTP allows multiple requests for a given TCP connection. Using the same HttpClient object allows the framework to maintain a TCP connection for multiple requests.

While it's true that the sample code performs just one request, note this text in the documentation:

The HttpClient class instance acts as a session to send HTTP requests and receive responses. An HttpClient instance is a collection of settings that apply to all requests executed by that instance. In addition, every HttpClient instance uses its own connection pool…

[emphasis mine]

For the object to act as "a collection of settings that apply to all requests executed by that instance", it is obvious it would have to be used for more than one request.

How to dispose HttpClient after it's finished?

So HttpClient is actually a bit weird in the context of being an IDisposable. Even though it implements the IDisposable interface, Microsoft actually advises against placing it in a using statement.

If you are using it in an ASP.NET Core context, you should use the HttpClientFactory to manage the lifetime of your HttpClients. If not, it is recommended to use a single static instance, but be wary that this can cause other issues, such as DNS staleness.

Should you call dispose on a HttpClient response object?

The general rule is: always call Dispose on objects implementing IDisposable. The reason you always want to do that is because you never know if the implementation will ever need to dispose some resources.

As you can see in the source, it does dispose the actual stream, so you really should dispose it.

You might want to do it in the receiving method. There is no need to copy the result and call dispose right away.

You could call it like this, like you are used to do:

using (var r = await DoSomething())
{
}

Should HttpClient instances created by HttpClientFactory be disposed?

Calling the Dispose method is not required but you can still call it if you need for some reasons.

Proof: HttpClient and lifetime management

Disposal of the client isn't required. Disposal cancels outgoing requests and guarantees the given HttpClient instance can't be used after calling Dispose. IHttpClientFactory tracks and disposes resources used by HttpClient instances. The HttpClient instances can generally be treated as .NET objects not requiring disposal.

Check the source of DefaultHttpClientFactory:

public HttpClient CreateClient(string name)
{
if (name == null)
{
throw new ArgumentNullException(nameof(name));
}

var handler = CreateHandler(name);
var client = new HttpClient(handler, disposeHandler: false);

var options = _optionsMonitor.Get(name);
for (var i = 0; i < options.HttpClientActions.Count; i++)
{
options.HttpClientActions[i](client);
}

return client;
}

The instance of HttpMessageHandler stores unmanaged resources of the HttpClient. In the classical scenario the HttpClient creates the instance of HttpMessageHandler and disposes it while itself disposing.

You can see in the above code that different instances of HttpClient shares single instance of HttpMessageHandler and doesn't dispose it (disposeHandler: false).

So, the call of the HttpClient.Dispose does nothing. But it's not dangerous.

Proper way of disposing HttpclientHandler

This answer will be short, but sweet:

Handlers are tied to the HttpClient at creation. You don't dispose of those. Just create your HttpClient with it and forget about it. That example on MS's site is not a typical usage scenario.

Make sure that when you create your HttpClient you make it static and in the class scope:

private static readonly HttpClient clientWithProxy = new HttpClient(handlerWithProxy);

You should use reuse the same HttpClient throughout the lifetime of your application for all HTTP requests.



Related Topics



Leave a reply



Submit