Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Which SendAsync method is called when a HttpClientHandler is passed to HttpClient

Most of the properties for customizing requests are defined in HttpClientHandler, this class is a subclass of HttpMessageHandler, the class defined like this:

public abstract class HttpMessageHandler : IDisposable
{
  protected internal abstract Task<HttpResponseMessage> SendAsync
    (HttpRequestMessage request, CancellationToken cancellationToken);
  public void Dispose();
  protected virtual void Dispose (bool disposing);
}

The book <C#5.0 in a nutshell> said the SendAsync method in HttpMessageHandler is called when we call HttpClient's SendAsync method. But the HttpClient class also defines a SendAsync method, when we call this method on an instance of HttpClient, which SendAsync is called?

like image 476
Allen4Tech Avatar asked Jan 07 '13 08:01

Allen4Tech


1 Answers

This is what's happening essentially:

HttpMessageInvoker & HttpClient

class HttpMessageInvoker
{
    private HttpMessageHandler handler;

    public HttpMessageInvoker(HttpMessageHandler handler)
    {
        this.handler = handler;
    }

    public virtual void SendAsync()
    {
        Console.WriteLine("HttpMessageInvoker.SendAsync");
        this.handler.SendAsync();
    }
}

class HttpClient : HttpMessageInvoker
{
    public HttpClient(HttpMessageHandler handler)
        : base(handler)
    {
    }

    public override void SendAsync()
    {
        Console.WriteLine("HttpClient.SendAsync");
        base.SendAsync();
    }
}

HttpMessageHandler & HttpClientHandler

abstract class HttpMessageHandler
{
    protected internal abstract void SendAync();
}

class HttpClientHandler : HttpMessageHandler
{
    protected internal override void SendAync()
    {
        Console.WriteLine("HttpClientHandler.SendAsync");
    }
}

So if you call SendAsync on an HttpClient instance, that method is executed. The method calls the SendAsync method from HttpMessageInvoker. This method calls the SendAsync method of a HttpMessageHandler instance. HttpMessageHandler is abstract; HttpClientHandler provides a concrete implementation of the abstract SendAync method by overriding it.

Example:

var handler = new HttpClientHandler();
var client = new HttpClient(handler);
client.SendAsync();

Output:

HttpClient.SendAsync
HttpMessageInvoker.SendAsync
HttpClientHandler.SendAsync
like image 170
dtb Avatar answered Oct 18 '22 04:10

dtb