美文网首页
什么!Sentinel流控规则可以这样玩?

什么!Sentinel流控规则可以这样玩?

作者: 牧小农 | 来源:发表于2022-05-25 09:23 被阅读0次

    点赞再看,养成习惯,微信搜索【牧小农】关注我获取更多资讯,风里雨里,小农等你,很高兴能够成为你的朋友。
    项目源码地址:公众号回复 sentinel,即可免费获取源码

    前言

    上一篇文章中,我们讲解了关于sentinel基本介绍以及流控规则中直接和快速失败的效果,有兴趣的可以去看上一篇文章,今天,我们给大家带来更加详细的关于sentinel流控规则的介绍。今天的内容我们主要围绕四个点进行展开介绍。

    • 流控模式 :关联、链路
    • 流控效果 :Warm Up、排队等待
    image.png

    这四点具体是什么意思呢?别急我们一个一个来做详细的介绍,首先我们从关联开始。

    首先启动项目:cloud-alibaba-sentinel-8006

    关联

    在官方的介绍中是这样说的:关联的资源达到阈值时,就限流自己。

    这句话是什么意思呢?用比较直白一点的话来讲,假设我们有A和B两个接口,当A关联B接口,同时B接口的资源达到设定的阈值时,限流A。我们也可以理解成,当我们下游的服务出现访问压力过大时,对上游的服务进行拦截和限流操作,例如:电商系统,当我们订单系统超出承受阈值时,对我们支付模块进行限流。

    image.png

    例如:当我们关联order接口达到我们设定的阈值时,限流pay的接口访问。

    @Slf4j
    @RestController
    public class TestController {
    
        @GetMapping("/pay")
        public String pay() {
            return "hello my name is pay ,wo shi boy";
        }
    
        @GetMapping("/order")
        public String order(){
            return "hi my name is order, me is girl";
        }
    
    }
    

    给pay接口添加流控规则

    image.png

    在这里我们需要使用到postMan工具,来模拟并发访问,用它来测试我们的order接口的并发访问。

    image.png image.png

    在这里的意思是25个线程0.25秒跑一次,当我们跑起来之后,再去访问pay接口就可以看到以下信息

    image.png image.png

    当我们对order接口进行并发访问的时候,这个时候我们去访问pay接口,就可以看到pay接口返回限流信息

    链路

    接下来我们就来看一下流控模式中的链路,链路的意思是值当某个接口过来的资源达到阈值时,开启限流,主要是针对于请求来源的微服务,具有更细颗粒度。

    比如在一个服务应用中,多个(pay和order)接口都调用了同一个服务中的方法(该方法必须使用注解 SentinelResource进行修饰),如果频繁的去请求pay接口,并且达到设定的阈值,这么时候我们再去请求order接口,那么调用了同一服务的order接口就会被限流

    image.png

    test类

    @Service
    public class TestService {
        // 定义限流资源
        @SentinelResource("end")
        public String end(){
            return "end method";
        }
    }
    

    controller类

    @Slf4j
    @RestController
    public class TestController {
    
        @Autowired
        private TestService testService;
    
        @GetMapping("/pay")
        public String pay() {
            return testService.end();
        }
    
        @GetMapping("/order")
        public String order(){
            return testService.end();
        }
    
    }
    

    配置项web-context-unify,这个配置的意思是说根据不同的URL进行链路限流,否则没有效果

    spring:
      application:
        name: cloudalibaba-sentinel-service
      cloud:
        nacos:
          discovery:
            server-addr: localhost:8848
        sentinel:
          transport:
            #配置Sentinel地址,就是我们的WEB界面
            dashboard: localhost:8080
            #Sentinel配置默认8719端口,被占用端口会自动从+1,直到找到未被占用的端口
            port: 8719
            # 配置为false
          web-context-unify: false
    

    我们访问pay接口和order接口后,需要对end进行流控规则的配置,也就是使用了SentinelResource注解标注的方法进行流控设置。

    image.png

    那么这个时候如果我们频繁的去访问order接口的时候,就会出现异常的情况,直接抛出错误提示,这个也是因为快速失败在链路上的直接体现

    image.png

    Warm Up

    参考文档:https://sentinelguard.io/zh-cn/docs/flow-control.html

    Warm Up 流量控制,也叫预热或者冷启动方式,会根据我们设定的规则,进行缓慢的流量放开,逐渐增加阈值上限,给系统一个反应时间,避免流量的突然增加,将系统压垮的情况发生,主要用于预防我们系统长期处于稳定的流量访问下,突然流量的增加,将系统资源直接拉满的情况.

    image.png

    在这里我们主要弄明白两个参数

    单机阈值:12,这个表示我们访问最大阈值为12,但是第一次最大访问量为4,为什么是4呢,看下面公式

    预热公式:阈值/coldFactor(默认值为3),经过预热时间后才会达到阈值。

    预热时长:5 ,也就是说我们的请求会在五秒内单机阈值达到12的访问,比如第一次为4,后续在五秒内依次5/6/8/10,最后达到12的阈值

    一般这种在秒杀或者电商节中会设置这样的流控规则,就是为了防止突然流量的增加导致系统的奔溃。

    当我们设置完流控规则以后,我们就来看一下效果,我们刚才设置的order的接口,如果当我们在频繁的去访问order接口的时候,如果超过当前时间设定的阈值时,直接返回限流信息。

    image.png

    在这里我们直接用浏览器疯狂的去刷新,是时候体验单身二十几年的手速了,当然也可以使用postman接口去试,我们这边手速比较快,直接用浏览器刷新,我们可以看到下面的曲线图:

    image.png

    蓝色表示你拒绝的QPS,绿色表示通过的QPS,我们可以看到蓝色成明显的下降趋势,而绿色成上升趋势,也可以通过右边的表格中看到,刚开始通过的只有四个,具体的有三个,后面通过慢慢增加,拒绝慢慢变少,这个就是我们Warm Up(预热)的作用了

    排队等待

    我们现在来介绍最后一个流控规则的使用,排队等待会严格控制请求通过的间隔时间,让请求稳定且匀速的通过,可以用来处理间隔性突发的高流量,例如抢票软件,在某一秒或者一分钟内有大量的请求到来,而接下来的一段时间里处于空闲状态,我们希望系统能够在接下来的空余时间里也能出去这些请求,而不是直接拒绝。

    image.png

    以固定的间隔时间让请求通过,当请求过来的时候,如果当前请求距离上一个请求通过的时间大于 规则预设值 ,则请求通过,如果当前请求预期通过时间小于 规则预设值 ,则进行排队等待,如果预期通过时间超过最大排队时间,直接拒绝请求。

    Sentinel排队等待是 漏铜算法+虚拟队列机制实现的,目前排队等待中不支持QPS>1000的场景

    image.png

    我们对pay接口进行设置,一秒钟只处理一个QPS请求,其他的排队,如果超过15秒则直接拒绝

    pay接口调整,这里我们给pay接口加上打印日志,方便我们看到具体效果

        @GetMapping("/pay")
        public String pay() {
    //        return "hello my name is pay ,wo shi boy";
            log.info("pay接口,请求线程为:"+Thread.currentThread().getName());
            return testService.end();
        }
    

    我们借助postman来进行调用,说明手速始终更不上工具,还是工具香,这里我们设置10个请求,没有间隔时间

    image.png

    从下图中我们可以看到,对于我们的请求,是一个QPS请求。


    image.png

    总结

    到这里呢,我们的流控规则就讲完了,主要是针对不同的规则进行不同的设定,来满足我们不用业务场景,可能会有一点点的小饶,但是如果亲自操作之后,会感觉原来是这样,感兴趣的小伙伴可以自己动手试一试,源码都已经上传了,只有动手了才能感受到其中的快乐,赶紧去试一试吧。

    我是牧小农,怕什么真理无穷,进一步有进一步的欢喜,大家加油!

    相关文章

      网友评论

          本文标题:什么!Sentinel流控规则可以这样玩?

          本文链接:https://www.haomeiwen.com/subject/yokeprtx.html