我正在尝试让timout政策正常运作。 在集成api时我有以下要求。
对于这项任务,我想使用Polly,在我看来这是一个很好的组件,可以帮助处理瞬态故障。但是,由于我对这项技术很陌生,我只想确定我是否正确实施。
首先,我已经像Polly一样创建了一个超时策略
var timeoutPolicy =
Policy.TimeoutAsync(
TimeSpan.FromSeconds( 20 ),
TimeoutStrategy.Optimistic,
async ( context, timespan, task ) => {
//write here the cancel request
} );
然后我准备执行政策
var policyResult = await timeoutPolicy.ExecuteAndCaptureAsync( async () => {
//make here the request 1
} );
我从文档中得到的结果是,如果在timeoutPolicy.ExecuteAndCaptureAsync
委托内发生了一个timout,Polly会自动调用onTimeout
委托。正确?
但我的问题是:
答案 0 :(得分:4)
我从文档中得到的是,如果在内部发生超时 ExecuteAndCaptureAsync委托Polly自动调用 onTimeout委托。正确?
如果在执行委托内发生异常,会发生什么?
因为您使用的是ExecuteAndCaptureAsync(...),所以例外是placed in policyResult.FinalException。
我应该在try catch中包装那个polly构造吗?
因为您使用的是ExecuteAndCaptureAsync(..),所以异常会放在policyResult.FinalException中,因此您不需要try-catch。
当我分析政策结果时,我如何理解超时是否已经发生?
TimeoutPolicy throws TimeoutRejectedException超时。因为您正在使用ExecuteAndCaptureAsync(...),所以您应该在policyResult.FinalException中找到该异常。
进一步评论。使用TimeoutStrategy.Optimisitic
based on co-operative cancellation by CancellationToken
,您应该执行取消令牌的委托:
var policyResult = await timeoutPolicy.ExecuteAndCaptureAsync(async (ct) => {
//make request 1, in a form which responds to the cancellation token ct
}, userCancellationToken /* CancellationToken.None is acceptable. Polly will merge its timing-out CancellationToken into ct, during policy execution. */
);
其次,作为在onRetryAsync: async ( context, timespan, task ) => { ... }
内调用取消请求的替代方法,您可以选择使用下面的模式使代码更顺序/更少嵌套:
var policyResult = await timeoutPolicy.ExecuteAndCaptureAsync(async (ct) => {
//make request 1, in a form which responds to the cancellation token ct
}, CancellationToken.None);
if (policyResult.Outcome == OutcomeType.Failure && policyResult.FinalException is TimeoutRejectedException)
{
//write here the cancel request
}
更新:调用取消请求将以任一方式工作 - 从onRetryAsync
内部,或顺序,如上所述。顺序版本的一个优点是,如果取消请求因异常而失败,它可以更容易推断出现的情况。使用嵌套方法(在onRetryAsync
中调用取消请求),最终捕获到policyResult.FinalException
的异常可能来自初始请求或取消请求 - 并且可能很难分辨哪个。