You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何将Polly V7标准CircuitBreaker策略迁移至V8?

Polly V7 标准断路器到 V8 的迁移方案

原 V7 策略代码与逻辑

int retryCount = 2;

PolicyBuilder policyBuilder = Policy
    .HandleInner<WebException>()
    .Or<WebException>()
    .Or<TimeoutException>()
    .Or<TimeoutRejectedException>();

AsyncCircuitBreakerPolicy asyncCircuitBreakerPolicy = policyBuilder
    .CircuitBreakerAsync(1, TimeSpan.FromSeconds(1), OnBreak, OnReset);

AsyncRetryPolicy asyncWaitAndRetry = policyBuilder
    .WaitAndRetryAsync(retryCount, SleepDurationProvider, OnRetry);

AsyncPolicyWrap defaultPolicy = Policy.WrapAsync(
    asyncCircuitBreakerPolicy,
    asyncWaitAndRetry);

原策略逻辑:触发指定异常时重试2次,累计3次失败后,异常传递至断路器并立即触发断路。

V8 的核心变化

Polly V8 移除了原“标准”断路器实现,替换为类似旧版“高级”断路器的机制,核心要求:

  • 必须设置不小于2的MinimumThroughput(统计窗口内的最小请求数)
  • 基于失败率而非固定失败次数判断断路条件
  • 默认重新抛出所有异常

现有迁移思路分析

你提到的调换重试与断路器顺序、设置MinimumThroughput = retryCount + 1和FailureRatio = 1的思路可行,但确实需要合理配置SamplingDuration——这个值需要覆盖「初始请求+2次重试」的总耗时(包括重试间隔),确保所有失败请求都被纳入统计窗口。

更贴合原逻辑的替代方案

方案1:保持原策略顺序,通过参数对齐行为

无需调整重试和断路器的嵌套顺序(和V7一致,重试在断路器内部),直接配置V8断路器参数匹配原逻辑:

  • 设置MinimumThroughput = 3:对应原逻辑中累计3次失败的触发条件
  • 设置FailureRatio = 1.0:要求统计窗口内100%失败才触发断路
  • SamplingDuration设置为足够覆盖3次请求周期的时间:比如假设单次请求超时5秒,重试间隔1秒,总耗时约为5+1+5+1+5=17秒,可以设置为TimeSpan.FromSeconds(20),确保3次失败都被统计到。

这种方式不需要改变原策略的执行顺序,最大程度保留原行为。

方案2:用V8新的ResiliencePipelineBuilder简化配置

V8的ResiliencePipelineBuilder支持链式组合策略,代码更简洁,同时完全匹配原逻辑:

int retryCount = 2;
var pipeline = new ResiliencePipelineBuilder()
    // 先配置重试策略,和原WaitAndRetry逻辑一致
    .AddRetry(new RetryStrategyOptions
    {
        MaxRetryAttempts = retryCount,
        DelayGenerator = args => ValueTask.FromResult(SleepDurationProvider(args.AttemptNumber)),
        OnRetry = args =>
        {
            OnRetry(args.Exception, args.AttemptNumber, args.Delay);
            return ValueTask.CompletedTask;
        },
        ShouldHandle = new PredicateBuilder()
            .Handle<WebException>()
            .Handle<TimeoutException>()
            .Handle<TimeoutRejectedException>()
    })
    // 再配置断路器,匹配原CircuitBreaker逻辑
    .AddCircuitBreaker(new CircuitBreakerStrategyOptions
    {
        MinimumThroughput = 3,
        FailureRatio = 1.0,
        BreakDuration = TimeSpan.FromSeconds(1),
        OnBreak = args =>
        {
            OnBreak(args.Exception, args.BreakDuration);
            return ValueTask.CompletedTask;
        },
        OnReset = () =>
        {
            OnReset();
            return ValueTask.CompletedTask;
        },
        ShouldHandle = new PredicateBuilder()
            .Handle<WebException>()
            .Handle<TimeoutException>()
            .Handle<TimeoutRejectedException>()
    })
    .Build();

这里的策略执行顺序和V7的WrapAsync一致(内部重试先执行,外部断路器后执行),参数配置完全对齐原逻辑的触发条件。

是否需要自定义ResilienceStrategy?

不需要。V8的内置重试和断路器策略通过参数配置完全可以模拟原V7标准断路器的行为,自定义策略会增加代码维护成本,优先使用内置配置实现即可。

内容的提问来源于stack exchange,提问作者user2727133

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.26 21:37:50