HttpClientFactory 结合 Polly 轻松实现重试机制
HttpClientFactory 結合 Polly 輕松實現重試機制
Intro
我們的服務里有一個 API 會去調用第三方的接口,設置了超時時間,最近偶爾會發生超時的情況,微軟在提供 HttpClientFactory 的同時,也提供了一個基于 Polly 的一個擴展,我們可以借助它輕松地實現重試,熔斷等行為。
Sample
使用 Polly 擴展需要引用 nuget 包 :Microsoft.Extensions.Http.Polly
使用示例:
services.AddHttpClient(ServiceConst.IterableHttpClientName,?x?=> {x.Timeout?=?new?TimeSpan(0,?0,?3); }).AddTransientHttpErrorPolicy(builder?=>{return?builder.Or<TaskCanceledException>().Or<OperationCanceledException>().Or<TimeoutException>().OrResult(res?=>?res.StatusCode?==?HttpStatusCode.TooManyRequests?||?(int)res.StatusCode?>=?500).RetryAsync(5);})通過 AddTransientHttpErrorPolicy 擴展方法來注冊一個 Polly 的 policy,具體可以通過 policyBuilder 委托來定制自己要處理的情況和 policy 行為,支持方式有很多可以簡單的指定重試,也可以指定 WaitANdRetryAsync 等待一段時間后重試,可以重試一次也可以一直重試下去,非常的靈活,可以根據自己的業務場景進行定制化配置,這里的示例直接是用了簡單的重試機制
單元測試
下面提供了一個測試重試的單元測試,也可以作為使用示例的一個參考:
[Fact] public?async?Task?TaskCanceledException() {var?ticks?=?new?ConcurrentBag<long>();var?retryLimit?=?5;var?services?=?new?ServiceCollection();services.AddHttpClient("test",?x?=>{x.Timeout?=?TimeSpan.FromSeconds(1);}).AddTransientHttpErrorPolicy(builder?=>{return?builder.Or<TaskCanceledException>().Or<OperationCanceledException>().Or<TimeoutException>().OrResult(res?=>res.StatusCode?==?HttpStatusCode.TooManyRequests?||?(int)res.StatusCode?>=?500).RetryAsync(retryLimit);}).AddHttpMessageHandler(()?=>?new?MockHttpHandler(request?=>{ticks.Add(DateTime.UtcNow.Ticks);throw?new?TaskCanceledException();}));await?using?var?provider?=?services.BuildServiceProvider();try{using?var?response?=?await?provider.GetRequiredService<IHttpClientFactory>().CreateClient("test").GetAsync("api/test");}catch?(Exception?e){Assert.True(e?is?OperationCanceledException);}Assert.Equal(retryLimit?+?1,?ticks.Count); }private?class?MockHttpHandler?:?DelegatingHandler {private?readonly?Func<HttpRequestMessage,?HttpResponseMessage>?_getResponseFunc;public?MockHttpHandler(Func<HttpRequestMessage,?HttpResponseMessage>?getResponseFunc){_getResponseFunc?=?getResponseFunc;}protected?override?Task<HttpResponseMessage>?SendAsync(HttpRequestMessage?request,?CancellationToken?cancellationToken){return?Task.FromResult(_getResponseFunc(request));} }More
除了 AddTransientHttpErrorPolicy 之外,Polly 擴展還支持 AddPolicyHandler/AddPolicyHandlerFromRegistry 擴展方法,有興趣的可以自己探索一下哈~~
Reference
https://www.nuget.org/packages/Microsoft.Extensions.Http.Polly
https://github.com/dotnet/aspnetcore/tree/master/src/HttpClientFactory/Polly/src
總結
以上是生活随笔為你收集整理的HttpClientFactory 结合 Polly 轻松实现重试机制的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 使用 C# 9 的records作为强类
- 下一篇: .netcore 极速接入第三方登录