1

我执行对不太稳定的外部服务的调用,因此引发 WebExceptions。
我想重试几次,在最后一次尝试之后,我想抛出收到的最后一个错误。

这是我对Polly (v6.1.1)的尝试:

public static Policy WaitAndRetryPolicy<T>(short nrOfRetryAttempts = 5) where T : Exception
{
    var waitAndRetry = Policy
        .Handle<T>()
        .WaitAndRetry(nrOfRetryAttempts, retryAttempt => TimeSpan.FromSeconds(Math.Pow(2, retryAttempt)));

    var fallbackForLastError = Policy
        .Handle<T>()
        .Fallback(
            fallbackAction: () => { },
            onFallback: (ex) => { throw ex; });

    return Policy.Wrap(fallbackForLastError, waitAndRetry);
}

调用者,旧版 VB.Net:

Dim retryPolicy = Policies.WaitAndRetryPolicy(Of WebException)()
Dim theResult = retryPolicy.
    ExecuteAndCapture(Function()
                          Return aProxy.GetSomething(a, b)
                      End Function).Result

当我运行上面描述的代码时,theResult保持为空,并且似乎没有调用该服务。如果我只使用 WaitAndRetryPolicy 而不使用Fallback函数,则会调用服务并且重试机制按预期工作(当然不会抛出异常)。

如何实现我的目标,而无需在调用者代码中检查PolicyResult.FinalException

4

2 回答 2

3

要让 Polly 重新抛出任何最终异常,而不是将其捕获到PolicyResult.FinalException中,只需使用.Execute(...)or.ExecuteAsync(...)重载执行策略,而不是.ExecuteAndCapture(...)or.ExecuteAndCaptureAsync(...)

于 2018-11-24T07:46:44.683 回答
0

我不知道最后一个异常,但我已经使用 Retry 和 CircuitBreakerException(with Wrapping) 实现了非常相似的行为。因此,您可以尝试 3 次,并在 2 次失败后抛出断路器异常。然后您就可以对最后一个异常做出反应。

Policy
.Handle<SomeExceptionType>()
.CircuitBreaker(2, TimeSpan.FromMinutes(x));
于 2018-11-23T16:48:49.573 回答