熔断降级会在调用链路中某个资源出现不稳定状态时(例如调用超时或异常比例升高),对这个资源的调用进行限制,让请求快速失败,避免影响到其它的资源而导致级联错误。当资源被降级后,在接下来的降级时间窗口之内,对该资源的调用都自动熔断(默认行为是抛出 DegradeException )。
1 重要的属性
Field | 说明 | 默认值 |
resource | 资源名,即限流规则的作用对象 | |
count | 阈值 | |
grade | 熔断策略,支持秒级 RT/秒级异常比例/分钟级异常数 | 秒级平均 RT |
timeWindow | 降级的时间,单位为 s | |
rtSlowRequestAmount | RT 模式下 1 秒内连续多少个请求的平均 RT 超出阈值方可触发熔断(1.7.0 引入) | 5 |
minRequestAmount | 异常熔断的触发最小请求数,请求数小于该值时即使异常比率超出阈值也不会熔断(1.7.0 引入) | 5 |
同一个资源可以同时有多个降级规则。
熔断策略详解:
- 平均响应时间 (DEGRADE_GRADE_RT):当 1s 内持续进入 N 个请求,对应时刻的平均响应时间(秒级)均超过阈值(count,以 ms 为单位),那么在接下的时间(DegradeRule 中的 timeWindow,以 s 为单位)之内,对这个方法的调用都会自动地熔断(抛出 DegradeException)。
- 异常比例 (DEGRADE_GRADE_EXCEPTION_RATIO):当资源的每秒请求量 >= N(可配置),并且每秒异常总数占通过量的比值超过阈值(DegradeRule 中的 count)之后,资源进入降级状态,即在接下的时间(DegradeRule 中的 timeWindow,以 s 为单位)之内,对这个方法的调用都会自动地返回。异常比率的阈值范围是 [0.0, 1.0],代表 0% - 100%。
- 异常数 (DEGRADE_GRADE_EXCEPTION_COUNT):当资源近 1 分钟的异常数目超过阈值之后会进行熔断。注意由于统计时间是分钟级别的,若 timeWindow小于 60s,则结束熔断状态后仍可能再进入熔断状态。
这里演示如何使用平均响应时间(DEGRADE_GRADE_RT)配置规则
2 实现步骤
熔断降级规则设置有两种方式
- 本地代码设置
- 在Sentinel控制台动态设置
平均响应时间
本地代码设置
1.导入资料中的sentinel_rule项目。
2.创建DegradeController,在其中编写修改以下代码
package com.example.demo.controller;
import com.alibaba.csp.sentinel.annotation.SentinelResource;
import com.alibaba.csp.sentinel.slots.block.BlockException;
import com.alibaba.csp.sentinel.slots.block.RuleConstant;
import com.alibaba.csp.sentinel.slots.block.degrade.DegradeRule;
import com.alibaba.csp.sentinel.slots.block.degrade.DegradeRuleManager;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import javax.annotation.PostConstruct;
import java.util.ArrayList;
import java.util.List;
@RestController
public class DegradeController {
//定义资源 value:设置资源的名称 blockHandler:设置限流或降级的处理函数
@SentinelResource(value = "Sentinel_Rule",blockHandler = "exceptionHandler")
@GetMapping("ann")
public String hello(){
//使用限流规则
return "Hello Sentinel!";
}
//被限流或降级的处理函数
public String exceptionHandler(BlockException e){
e.printStackTrace();
return "系统繁忙,请稍候";
}
}
3.在DegradeController中编写以下代码
//定义熔断降级规则
@PostConstruct
public void initDegradeRule(){
//1.创建存放规则的集合
List<DegradeRule> rules = new ArrayList<>();
//2.创建熔断降级规则
DegradeRule rule = new DegradeRule();
//定义资源名称
rule.setResource("Sentinel_Rule");
//定义规则类型 RuleConstant.DEGRADE_GRADE_RT:秒级RT 平均响应时间类型
rule.setGrade(RuleConstant.DEGRADE_GRADE_RT);
//定义阈值
rule.setCount(0.01);
//定义降级时间
rule.setTimeWindow(10);
//3.将规则保存到集合中
rules.add(rule);
//4.加载规则
DegradeRuleManager.loadRules(rules);
}
4.运行测试
通过浏览器输入http://localhost:8080/ann,慢速刷新,则持续显示”Hello Sentinel”;快速刷新多次之后则会出现“系统繁忙,请稍候”,并且之后再次刷新都显示“系统繁忙,请稍候”,等待10秒之后,则再次显示“Hello Sentinel”,这说明对资源限流成功。
3 在Sentinel控制台动态设置
将DegradeController中的代码设置熔断降级规则删除,重启项目,在Sentinel控制台动态设置熔断降级规则。
在Sentinel控制台的左侧菜单中选择“降级规则”,点击“新增降级规则”按钮,设置熔断降级规则,其中降级策略设选择“RT”。
之后,通过浏览器输入http://localhost:8080/ann,慢速刷新,则持续显示”Hello Sentinel”;快速刷新多次之后则会出现“系统繁忙,请稍候”,并且之后再次刷新都显示“系统繁忙,请稍候”,等待10秒之后,则再次显示“Hello Sentinel”,这说明对资源限流成功。