soul源码解读(十八)-- resilience4j插件原理分析

17 篇文章 0 订阅

soul源码解读(十八)

resilience4j

resilience4j插件是网关用来对流量进行限流与熔断的可选选择之一。

resilience4j为网关熔断限流提供能力。

插件使用

1.启动 admin,打开 resilience4j 插件开关

2.在 bootstrap 项目的 pom 文件引入 resilience4j 插件的相关依赖,启动 bootstrap

	<!-- soul resilience4j plugin start-->
  	<dependency>
      	<groupId>org.dromara</groupId>
      	<artifactId>soul-spring-boot-starter-plugin-resilience4j</artifactId>
       	<version>${last.version}</version>
  	</dependency>
	<!-- soul resilience4j plugin end-->

3.启动一个 http 服务,这里我们启动 soul-examples-http 服务

4.配置限流参数
在 admin 后台选择 resilience4j 插件,添加选择器
在这里插入图片描述

然后添加规则
在这里插入图片描述

Resilience4j参数详解:

  • timeoutDurationRate:等待获取令牌的超时时间,单位ms,默认值:5000。

  • limitRefreshPeriod:刷新令牌的时间间隔,单位ms,默认值:500。

  • limitForPeriod:每次刷新令牌的数量,默认值:50。

  • circuitEnable:是否开启熔断,0:关闭,1:开启,默认值:0。

  • timeoutDuration:熔断超时时间,单位ms,默认值:30000。

  • fallbackUri:降级处理的uri。

  • slidingWindowSize:滑动窗口大小,默认值:100。

  • slidingWindowType:滑动窗口类型,0:基于计数,1:基于时间,默认值:0。

  • minimumNumberOfCalls:开启熔断的最小请求数,超过这个请求数才开启熔断统计,默认值:100。

  • waitIntervalFunctionInOpenState:熔断器开启持续时间,单位ms,默认值:10。

  • permittedNumberOfCallsInHalfOpenState:半开状态下的环形缓冲区大小,必须达到此数量才会计算失败率,默认值:10。

  • failureRateThreshold:错误率百分比,达到这个阈值,熔断器才会开启,默认值50。

  • automaticTransitionFromOpenToHalfOpenEnabled:是否自动从open状态转换为half-open状态,,true:是,false:否,默认值:false。

源码分析

我们看下 Resilience4JPlugin 的代码

// Resilience4JPlugin.java
protected Mono<Void> doExecute(final ServerWebExchange exchange, final SoulPluginChain chain, final SelectorData selector, final RuleData rule) {
        ...
        // 检测数据,如果某个参数没设置值就给个默认值
        resilience4JHandle = resilience4JHandle.checkData(resilience4JHandle);
        // 判断熔断有没有打开 0关闭 1打开
        if (resilience4JHandle.getCircuitEnable() == 1) {
            return combined(exchange, chain, rule);
        }
        // 熔断开关没有打开,就直接走限流的逻辑
        return rateLimiter(exchange, chain, rule);
    }

接下来我们 combined 里的逻辑

// Resilience4JPlugin.java
private Mono<Void> combined(final ServerWebExchange exchange, final SoulPluginChain chain, final RuleData rule) {
		// 根据规则build一个熔断限流配置对象
        Resilience4JConf conf = Resilience4JBuilder.build(rule);
        return combinedExecutor.run(
        		// 请求成功,判断返回的status是不是等于200,如果status为空或者不等于200就抛异常
                chain.execute(exchange).doOnSuccess(v -> {
                    HttpStatus status = exchange.getResponse().getStatusCode();
                    if (status == null || !status.is2xxSuccessful()) {
                        exchange.getResponse().setStatusCode(null);
                        throw new CircuitBreakerStatusCodeException(status == null ? HttpStatus.INTERNAL_SERVER_ERROR : status);
                    }
                }), 
          // 请求失败调用fallbackUrl      
		fallback(combinedExecutor, exchange, conf.getFallBackUri()), conf);
    }

接下来我们看下 combinedExecutor#run 里的代码

// CombinedExecutor.java
public <T> Mono<T> run(final Mono<T> run, final Function<Throwable, Mono<T>> fallback, final Resilience4JConf resilience4JConf) {
	// 获取限流的配置
    RateLimiter rateLimiter = Resilience4JRegistryFactory.rateLimiter(resilience4JConf.getId(), resilience4JConf.getRateLimiterConfig());
    // 获取熔断的配置
    CircuitBreaker circuitBreaker = Resilience4JRegistryFactory.circuitBreaker(resilience4JConf.getId(), resilience4JConf.getCircuitBreakerConfig());
    // //首先执行熔断器
    Mono<T> to = run.transformDeferred(CircuitBreakerOperator.of(circuitBreaker))
            //再执行限流
            .transformDeferred(RateLimiterOperator.of(rateLimiter))
            .timeout(resilience4JConf.getTimeLimiterConfig().getTimeoutDuration())
            .doOnError(TimeoutException.class, t -> circuitBreaker.onError(
                    resilience4JConf.getTimeLimiterConfig().getTimeoutDuration().toMillis(),
                    TimeUnit.MILLISECONDS,
                    t));
    if (fallback != null) {
    	//降级处理
        to = to.onErrorResume(fallback);
    }
    return to;
}

总结

resilience4j 可以根据配置只开启限流,或者开启熔断加限流。
然后会先执行熔断逻辑,再判断限流。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值