Search code examples
c#.net.net-6.0dotnet-httpclientpolly

How to use the PolicyHttpMessageHandler as "standalone"?


I'm just trying to create a simple test where I use DelegateHandlers to instantiate a HttpClient without bringing Asp.net Core packages. I have 2 deletage handlers

  • ThrottlingDelegatingHandler
  • PolicyHttpMessageHandler (from Polly package)

How can I combine both and pass to the HttpClient?

var policy = HttpPolicyExtensions.HandleTransientHttpError().CircuitBreakerAsync(5, TimeSpan.FromSeconds(30));
var pollyHandler = new PolicyHttpMessageHandler(policy);
var http = new HttpClient(new ThrottlingDelegatingHandler(MaxParallelism, pollyHandler));

The above gives me an error: System.InvalidOperationException : The inner handler has not been assigned.

The PolicyHttpMessageHandler does not have a constructor where I can pass the innerHandler.

How can I accomplish this?


Solution

  • You have to set the InnerHandler in your most inner handler to HttpClientHandler like this:

    var policy = HttpPolicyExtensions.HandleTransientHttpError().CircuitBreakerAsync(5, TimeSpan.FromSeconds(30));
    var pollyHandler = new PolicyHttpMessageHandler(policy);
    
    //New line
    pollyHandler.InnerHandler = new HttpClientHandler();
    
    var http = new HttpClient(new ThrottlingDelegatingHandler(MaxParallelism, pollyHandler));
    

    You basically have to set the next handler in the pipeline.


    For reference: this is how HttpClient is constructed if no handler is specified

    #region Constructors
    
    public HttpClient() : this(new HttpClientHandler())
    {
    }
    
    public HttpClient(HttpMessageHandler handler) : this(handler, true)
    {
    }
    
    public HttpClient(HttpMessageHandler handler, bool disposeHandler) : base(handler, disposeHandler)
    {
        _timeout = s_defaultTimeout;
        _maxResponseContentBufferSize = HttpContent.MaxBufferSize;
        _pendingRequestsCts = new CancellationTokenSource();
    }
    
    #endregion Constructors
    

    Where the base is the HttpMessageInvoker class