[英]retry polly unit testing (xunit and moq)
我有 .net 核心 weabpi(見下面的代碼)。 我正在使用 polly 重試策略(請參閱下面的策略)。 我想對端點(getProducts)進行單元測試並測試 polly 重試
我找到了這些示例,但不清楚如何對端點進行單元測試和重試策略?
services
.AddHttpClient<IProductService, ProductService>()
.AddPolicyHandler(GetRetryPolicy(3, 2));
static IAsyncPolicy<HttpResponseMessage> GetRetryPolicy(int retryCount, int breakDuration)
{
return HttpPolicyExtensions
.HandleTransientHttpError()
.OrResult(msg => msg.StatusCode == System.Net.HttpStatusCode.NotFound)
.WaitAndRetryAsync(retryCount, retryAttempt => TimeSpan.FromSeconds(Math.Pow(breakDuration,
retryAttempt)));
}
.Net核心api:
public interface IProductService
{
Task<IEnumerable<ProductResponse>> GetProducts(string productType);
}
public class ProductService: IProductService
{
private readonly HttpClient _httpClient;
public ProductService(HttpClient httpClient)
{
_httpClient = httpClient;
}
public async Task<IEnumerable<ProductResponse>> GetProducts(string productType)
{
var response = await _httpClient.GetAsync("uri");
...
}
}
第一的
我建議您在策略中添加帶有抖動退避的等待和重試。
像這樣的東西:
var delay = Backoff.DecorrelatedJitterBackoffV2(medianFirstRetryDelay: TimeSpan.FromMilliseconds(100), policyRetryCount);
RetryPolicy retryPolicy = Policy
.Handle<YourException>()
.WaitAndRetry(delay);
然后,只需Mock
您的服務並對其進行測試,例如:
Mock<IProductService> mockedProductService = new Mock<IProductService>();
mockedProductService.Setup(service => service.GetProducts(productType))
.ThrowsYourException();
var result = yourTestingMehtod
Assert.IsNotNull(result);
mockedProductService.Verify(service => service.GetProducts(productType), Times.Exactly(expectedServiceCall));
// example, expectedServiceCall is when you set retryCount 3, it will be 4
更新
我想您正在調用您的服務,例如:
retryPolicy.Execute(() => productService.GetProducts())
可悲的事實是,您無法真正對重試+端點邏輯進行單元測試,這是我的理由:
AddPolicyHandler
) 在HttpClient
的頂部注冊。 當您進行單元測試時,您不依賴於 DI,而是依賴於單個組件。回到你的測試用例。 用 given-when-then 結構表達測試場景的正確方法應該這樣寫
這不是單元測試。 它更像是一個組件/集成測試。 為什么? 因為即使您可以創建一個 HttpClient 模擬,但在這種情況下,那里不會有重試策略。
有一個解決方法:您可以通過PolicyHttpMessageHandler
使用策略手動裝飾底層處理程序。 但這在單元測試中是個壞主意,因為您基本上在測試中重新實現了 DI 部分。 這樣,您將測試您的測試安排代碼,而不是您的生產代碼。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.