配置
<!--sentinel-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>
</dependency>
spring:
cloud:
sentinel:
transport:
dashboard: localhost:8080
雪崩问题
- 微服务调用链路中的某个服务故障,引起整个链路中的所有微服务都不可用,这就是雪崩‘
- 解决方案
- 超时处理:设定超时时间,请求超过一定时间没有响应就返回错误信息,不会无休止等待。
- 舱壁模式:限定每个业务能使用的线程数,避免耗尽整个tomcat的资源,因此也叫线程隔离。‘
- 熔断降级:由断路器统计业务执行的
异常比例
,如果超出阈值
则会熔断该业务,拦截访问该业务的一切请求。 - 流量控制:限制业务访问的QPS,避免服务因流量的突增而故障。
流量控制
避免因瞬间的高并发流量而导致服务故障超时处理、线程隔离、降级熔断
避免因服务故障而引起的雪崩问题
限流规则
簇点链路:就是项目内的调用链路,链路中被监控的每个接口就是一个资源。默认情况下sentinel会监控SpringMVC的每一个端点(Endpoint),@RequestMapping标记的方法。
流控模式-直接
给 /order/{orderId}
这个资源设置流控规则,QPS不能超过 5。
流控模式-关联
统计与当前资源相关的另一个资源,触发阈值时,对当前资源限流
当/order/update
资源被访问的QPS超过5时,对/order/query
请求限流
流控模式-链路
只针对从指定链路访问到本资源的请求做统计,判断是否超过阈值。
-
Sentinel默认只标记Controller中的方法为资源,如果要标记其它方法,需要利用
@SentinelResource
注解@SentinelResource("goods") public void queryGoods() { }
-
Sentinel默认会将Controller方法做context整合,导致链路模式的流控失效,需要修改application.yml,添加配置
spring: cloud: sentinel: web-context-unify: false # 关闭context整合
-
两条请求链路:
- /save -> /goods
- /query -> /goods
只希望限制从/save进入到/goods的请求,则可以这样配置
流控效果
快速失败
达到阈值后,新的请求会被立即拒绝并抛出FlowException异常。是默认的处理方式
warm up
预热模式,对超出阈值的请求同样是拒绝并抛出异常。但这种模式阈值会动态变化,从一个较小值逐渐增加到最大阈值。
请求阈值初始值是 threshold / coldFactor,持续指定时长后,逐渐提高到threshold值。而coldFactor的默认值是3.
例如,我设置QPS的threshold为10,预热时间为5秒,那么初始阈值就是 10 / 3 ,也就是3,然后在5秒后逐渐增长到10.
给/order/{orderId}
这个资源设置限流,最大QPS为10,利用warm up效果,预热时长为5秒
排队等待
让所有的请求按照先后次序排队执行,两个请求的间隔不能小于指定时长
当请求超过QPS阈值时,排队等待
让所有请求进入一个队列中,然后按照阈值允许的时间间隔依次执行。后来的请求必须等待前面执行完成,如果请求预期的等待时间超出最大时长,则会被拒绝。
例如:QPS = 5,意味着每200ms处理一个队列中的请求;timeout = 2000,意味着预期等待超过2000ms的请求会被拒绝并抛出异常
热点参数限流
分别统计
参数相同
的请求,判断是否超过QPS阈值。
热点参数限流对默认的SpringMVC资源无效,需要@SentinelResource("hot")
对hot这个资源的0
号参数(第一个参数)做限流,每1秒相同参数的请求数不能超过5
有两个例外:
如果参数值是100,则每1秒允许的QPS为10
如果参数值是101,则每1秒允许的QPS为15