springboot 之 dubbo 使用sentinel熔断降级 (慢调用比例)

官方git地址: https://github.com/alibaba/Sentinel/wiki/%E7%86%94%E6%96%AD%E9%99%8D%E7%BA%A7
 
使用场景: 项目调用了别人提供的dubbo接口,为避免dubbo服务出现异常,导致dubbo消费者服务异常,所以需要设置熔断降级规则,保护dubbo消费者服务。
 
1.引入依赖
    com.alibaba.csp
    sentinel-core
    1.8.0
    com.alibaba.csp
    sentinel-annotation-aspectj
    1.8.0
    com.alibaba.csp
    sentinel-apache-dubbo-adapter
    1.8.0
 
2.初始化熔断降级规则--可在启动类中直接调用
public class App {
    public static void main(String[] args) {
        SpringApplication.run(App.class);
        initFlowRules();
    }
}
private static final String KEY = "com.huobi.dgg.uc.facade.LoginFacadeService:checkLogin(java.lang.String)"; // 针对方法级的熔断
private static final String KEY2 = "com.huobi.dgg.uc.facade.LoginFacadeService";  // 针对类级的熔断
private static void initFlowRules() {
    List rules = new ArrayList<>();
    DegradeRule rule = new DegradeRule( KEY)
             // 熔断策略,支持慢调用比例/异常比例/异常数策略
            .setGrade(CircuitBreakerStrategy. SLOW_REQUEST_RATIO.getType())
            // 慢调用比例模式下为慢调用临界 RT(超出该值计为慢调用),Max allowed response time,单位 ms
            .setCount(1000 * 3)
            //熔断时长,单位为 s, Retry timeout (in second)
            .setTimeWindow(5)
            // 慢调用比例阈值 Circuit breaker opens when slow request ratio > 60%
            .setSlowRatioThreshold(0.8)
            // 熔断触发的最小请求数,请求数小于该值时即使异常比率超出阈值也不会熔断
            .setMinRequestAmount(1000)
            // 统计时长(单位为 ms) 20000
            .setStatIntervalMs(1000 * 60);
    rules.add(rule);
    DegradeRuleManager. loadRules(rules);
    log.info("Degrade rule loaded[{}]", rules);
}
 
3.使用@SentinelResource注解定义资源,注解方式定义资源支持自动统计业务异常,无需手动调用 Tracer.trace(ex) 来记录业务异常
@Slf4j
@Service
public class UcService {
    @DubboReference(group = "${dubbo.group}", version = "${dubbo.version}")
    private Service service;
 
    @SentinelResource(value = "checkLogin")
    public Result checkLogin(String token) {
        return service.checkLogin(token);
    }
 
}
 

注:完成以上3步,spring boot 即可支持sentinel deubbo熔断降级。

 
该注解的功能相当于SphU. entry的功能,
private static AtomicInteger total = new AtomicInteger();
private static AtomicInteger pass = new AtomicInteger();
private static AtomicInteger block = new AtomicInteger();
 
public UserDO readUserInfo(String token) {
    Result result;
    Entry entry = null;
 
    try {
        // 有可能被编码了,尝试解码
        if (token.indexOf('%') != -1) {
            token = URLDecoder. decode(token, "utf-8");
        }
        entry = SphU. entry("com.huobi.dgg.uc.facade.LoginFacadeService:checkLogin(java.lang.String)");
        pass.incrementAndGet();
        result = loginFacadeService.checkLogin(token);
    } catch (BlockException e) {
        block.incrementAndGet();
        log.info("熔断。。。。");
        return null;
    } catch (Exception e) {
        block.incrementAndGet();
        log.error("调用uc dubbo checkLogin异常", e);
        return null;
    } finally {
        total.incrementAndGet();
        if (entry != null) {
            entry.exit();
        }
    }
 
    if (result != null && result.isSuccess()) {
        return result.getData();
    }
    if (null == result) {
        log.error("调用uc dubbo checkLogin返回null");
    } else {
        log.info("调用uc dubbo checkLogin返回码[{}], 返回信息[{}]", result.getCode(), result.getMessage());
    }
    if (env.equalsIgnoreCase("local")) {
        UserDO userDO = new UserDO();
        userDO.setId(110L);
        return userDO;
    }
    return null;
}
 
 
 
 

你可能感兴趣的:(springboot,dubbo,sentinel,java,spring,dubbo)