java web流量阀值系统_【SpringCloud】Spring Cloud Alibaba 之 Sentinel流量控制(三十)...

Sentinel流量控制用于监控应用流量,防止被瞬时高峰冲击。本文介绍了FlowSlot、限流规则及策略,包括QPS和并发线程数限流,并通过实例展示了快速失败、预热(Warm Up)、匀速排队三种流控效果。此外,还探讨了关联和链路限流模式。
摘要由CSDN通过智能技术生成

Sentinel流量控制介绍

流量控制(flow control),其原理是监控应用流量的 QPS 或并发线程数等指标,当达到指定的阈值时对流量进行控制,以避免被瞬时的流量高峰冲垮,从而保障应用的高可用性。

FlowSlot 会根据预设的规则,结合前面 NodeSelectorSlot、ClusterNodeBuilderSlot、StatisticSlot 统计出来的实时信息进行流量控制。

限流的直接表现是在执行 Entry nodeA = SphU.entry(resourceName) 的时候抛出 FlowException 异常。FlowException 是 BlockException 的子类,您可以捕捉 BlockException 来自定义被限流之后的处理逻辑。

同一个资源可以创建多条限流规则。FlowSlot 会对该资源的所有限流规则依次遍历,直到有规则触发限流或者所有规则遍历完毕。

一条限流规则主要由下面几个因素组成,我们可以组合这些元素来实现不同的限流效果:

resource:资源名,即限流规则的作用对象

count: 限流阈值

grade: 限流阈值类型(QPS 或并发线程数)

limitApp: 流控针对的调用来源,若为 default 则不区分调用来源

strategy: 调用关系限流策略

controlBehavior: 流量控制效果(直接拒绝、Warm Up、匀速排队)

以下是关于流量控制中名词解析

资源名:唯一名称、默认请求路径

针对来源:Sentinel可以针对调用者进行限流,填写微服务名,默认default(不区分来源)

阀值类型/单机阀值:

QPS(每秒钟的请求数量):当调用该api的QPS达到阀值的时候,进行限流

线程数:当调用该api的线程数达到阀值的时候,进行限流

是否集群:不需要集群

流控模式:

直接:api达到限流条件时,直接限流

关联:当关联的资源达到阀值时,就限流自己

链路:只记录指定链路上的流量(指定资源从入口资源进来的流量,如果达到阀值,就限流)【api级别的针对来源】

流控效果:

快速失败:直接失败,抛异常

Warm Up:根据codeFactor(冷加载因子,默认3)的值,从阀值/codeFactor,经过预热时长,才达到设置的QPS阀值

排队等待:匀速排队,让请求以均匀的速度通过,阀值类型必须设置为QPS,否则无效

Sentinel流量控制Demo

基于QPS的流量控制

当 QPS 超过某个阈值的时候,则采取措施进行流量控制。流量控制的效果包括以下几种:直接拒绝、Warm Up、匀速排队。对应 FlowRule 中的 controlBehavior 字段。

1、搭建项目,Controller内容如下:

1 @RestController2 public classFlowLimitController {3

4 @GetMapping("/testA")5 publicString testA(){6 return "--------testA";7 }8

9 @GetMapping("/testB")10 publicString testB(){11 return "--------testB";12 }13 }

2、将项目启动,以及Sentinel启动,添加流控规则,如下:

f13aba1ec1babbdc9698199f185a02a8.png

3、设置流控规则,每秒钟的请求数量为1,流控效果为快速失败,如下,保存后,即生效

780b20a6d11a518eef6464897db8a331.png

4、测试

1)浏览器访问地址:http://localhost:8401/testA,正常访问

b9182b65ce89a2d4fcbb54ad51639392.png

2)快速点击浏览器刷新按钮,刷新界面,页面显示:Blocked by Sentinel (flow limiting)

f9e034383ea9c1edb0da6b881d1aaf4d.png

基于并发数的流量控制

1、继续使用以上项目,修改testA方法,如下:

1 @GetMapping("/testA")2 publicString testA(){3 try{4 Thread.sleep(800);5 } catch(InterruptedException e) {6 e.printStackTrace();7 }8 return "--------testA";9 }

2、编辑流量规则,将流控规则改为当调用该api的线程数达到1的时候,进行限流,如下:

5b44bf13961fcfe16c5c4fdf0e352c91.png

3、测试

1)重新启动项目

2)使用浏览器单次请求,http://localhost:8401/testA,正常显示

2)使用JMeter进行并发测试请求:http://localhost:8401/testA,响应内容为:Blocked by Sentinel (flow limiting)

流控模式:直接

上面2个例子,流控模式都是直接,对自己本身资源的限制。

流控模式:关联

当两个资源之间具有资源争抢或者依赖关系的时候,这两个资源便具有了关联。像对数据库同一个字段的读操作和写操作存在争抢,读的速度过高会影响写得速度,写的速度过高会影响读的速度。如果放任读写操作争抢资源,则争抢本身带来的开销会降低整体的吞吐量。

示例

1、项目代码还是以上的项目代码

2、编辑流量规则,设置资源testA关联的testB,当testB达到阀值时,testA被限流。如下:

13eee7fb336ad4109aabde16aa2167b9.png

3、测试

1)启动项目

2)使用浏览器请求,http://localhost:8401/testA,正常显示

3)使用JMeter不停的循环请求:http://localhost:8401/testB,testB请求结果都正确

4)然后使用浏览器请求,http://localhost:8401/testA,无法正常显示,资源限制

流控模式:链路

1、项目代码还是以上的项目代码,Controllerh中testB方法

1 @GetMapping("/testB")2 publicString testB(){3 return "--------testB";4 }

2、查看簇点链路,发现/test,资源入口是sentinel_web_servlet_context

1c77db91a8afde4b501f47533328cf2b.png

3、删除其他流控规则,新增流量规则,设置资源testB链路限流,如下:、

c66a3baefc265be423a0c7f44c925055.png

4、测试

1)启动项目

2)使用浏览器请求,http://localhost:8401/testB,正常显示

3)快速点击浏览器刷新按钮,刷新界面,页面显示:Blocked by Sentinel (flow limiting)

流控效果:快速失败

以上例子显示了快速失败的效果,快速失败(RuleConstant.CONTROL_BEHAVIOR_DEFAULT)方式是默认的流量控制方式,当QPS超过任意规则的阈值后,新的请求就会被立即拒绝,拒绝方式为抛出FlowException。这种方式适用于对系统处理能力确切已知的情况下,比如通过压测确定了系统的准确水位时。

流控效果:Warm Up(预热)

Warm Up(RuleConstant.CONTROL_BEHAVIOR_WARM_UP)方式,即预热/冷启动方式。当系统长期处于低水位的情况下,当流量突然增加时,直接把系统拉升到高水位可能瞬间把系统压垮。通过"冷启动",让通过的流量缓慢增加,在一定时间内逐渐增加到阈值上限,给冷系统一个预热的时间,避免冷系统被压垮。

应用场景:

如:秒杀系统在开启瞬间,会有很多流量上来,很有可能把系统打死,预热方式就是把为了保护系统,可慢慢的把流量放进来,慢慢的把阀值增长到设置的阀值

案例:

阀值为10 + 预热时长设置5秒

系统初始化的阀值为10/3 约等于 3,即阀值刚开始为3;然后过了5秒阀值才慢慢升高恢复到10

1、项目代码还是以上的项目代码,Controllerh中testC方法

1 @GetMapping("/testC")2 publicString testC(){3 return "--------testC";4 }

2、新增流量规则,设置资源testC,单机阀值为10,流控效果为Warm Up,预热时长为5秒,如下:

12c7f79ae3b2bc4a23049bfad8f5a4b3.png

3、测试

1)启动项目

2)使用浏览器访问地址,http://localhost:8401/testC,正常显示

3)以每秒5次的刷新,一直刷新界面,效果,可以看到部分请求返回错误

4)5秒钟过后,还是以以每秒5次的刷新速度,刷新界面,请求正常

流控效果:排队等待

排队等待(RuleConstant.CONTROL_BEHAVIOR_RATE_LIMITER)方式会严格控制请求通过的间隔时间,也即是让请求以均匀的速度通过,对应的是漏桶算法。

这种方式主要用于处理间隔性突发的流量,例如消息队列。想象一下这样的场景,在某一秒有大量的请求到来,而接下来的几秒则处于空闲状态,我们希望系统能够在接下来的空闲期间逐渐处理这些请求,而不是在第一秒直接拒绝多余的请求。

案例

1、项目代码还是以上的项目代码,Controllerh中testA方法

1 @GetMapping("/testA")2 publicString testA(){3 try{4 Thread.sleep(800);5 } catch(InterruptedException e) {6 e.printStackTrace();7 }8 return "--------testA";9 }

2、新增流量规则,设置资源testA,流控效果为排队等待,超时时间为20000毫秒,如下:

e689ccde76d071a6576f7579398b772f.png

3、测试

1)启动项目

2)使用浏览器访问地址,http://localhost:8401/testA,正常显示

3)使用JMeter并发10个请求,执行一次,观察10次执行结果

4)所有请求都成功了,请求响应时间逐渐增加

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值