Polly策略组合及Fallback策略中获取已处理异常的实现方案
Polly策略组合问题解答
用户代码
// User Code .. code that can throw exceptions "Success"
现有策略定义
P1 策略
Policy .Handle<CosmosException>(fun cx -> cx.StatusCode = HttpStatusCode.TooManyRequests) .WaitAndRetryForever((fun _ cx _ -> (cx :?> CosmosException).RetryAfter.Value), (fun _ _ _ _ -> ()))
P2 策略
Policy<string> .Handle<Exception>() .Fallback("Failure")
P3 策略(原写法存在重载匹配问题)
// 原写法(无法编译) Policy<string> .Handle<Exception>() .Fallback(fun ex -> ex.Message)
问题1:组合P1与P2策略
需将P1转换为泛型Policy<string>(与P2类型匹配),再通过Wrap方法将重试策略(P1)作为内层策略,降级策略(P2)作为外层策略。异常会先经过内层重试逻辑,不符合重试条件的异常才会触发外层降级逻辑。
组合后的策略代码
let p = // 外层:P2降级策略,处理所有未被内层处理的异常 Policy<string> .Handle<Exception>() .Fallback("Failure") // 内层:P1重试策略,仅处理Cosmos的TooManyRequests异常 .Wrap( Policy<string> .Handle<CosmosException>(fun cx -> cx.StatusCode = HttpStatusCode.TooManyRequests) .WaitAndRetryForever( (fun _ cx _ -> (cx :?> CosmosException).RetryAfter.Value), (fun _ _ _ _ -> ()) // 空的重试回调 ) )
策略效果
- 用户代码执行成功:直接返回
"Success" - 抛出符合条件的
CosmosException:触发内层永久重试,直到成功 - 抛出其他异常:内层策略不处理,外层返回
"Failure"
问题2:编写P3策略并与P1组合
修正后的P3策略
Polly同步Fallback重载中,可通过DelegateResult<T>参数获取捕获到的异常。F#中需明确参数类型,以此提取异常消息:
let p3 = Policy<string> .Handle<Exception>() .Fallback(fun (result : DelegateResult<string>) -> // 提取捕获到的异常消息作为返回值 result.Exception.Message )
组合P1与P3得到PFinal
同样使用Wrap方法,将P1作为内层重试策略,P3作为外层降级策略:
let pFinal = // 外层:P3降级策略,返回异常消息 Policy<string> .Handle<Exception>() .Fallback(fun (result : DelegateResult<string>) -> result.Exception.Message) // 内层:P1重试策略 .Wrap( Policy<string> .Handle<CosmosException>(fun cx -> cx.StatusCode = HttpStatusCode.TooManyRequests) .WaitAndRetryForever( (fun _ cx _ -> (cx :?> CosmosException).RetryAfter.Value), (fun _ _ _ _ -> ()) ) )
策略效果
- 用户代码执行成功:返回
"Success" - 抛出符合条件的
CosmosException:触发永久重试 - 抛出其他异常:返回该异常的
Message属性内容
内容的提问来源于stack exchange,提问作者Franco Tiveron
相关产品推荐
相关产品推荐

