分布式系统中的限流与熔断

在应对秒杀、大促、双 11、618 等高性能压力的场景时,限流已经成为了标配技术解决方案,为保证系统的平稳运行起到了关键性的作用。不管应用场景是哪种,限流无非就是针对超过预期的流量,通过预先设定的限流规则选择性的对某些请求进行限流“熔断”。

1. 限流

  1.1 单机限流

    a>>限制并发量

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Semaphore;

public class SemaphoreTest {

    private static final int THREAD_COUNT = 30;

    private static ExecutorService threadPool = Executors
            .newFixedThreadPool(THREAD_COUNT);

    private static Semaphore s = new Semaphore(10);

    public static void main(String[] args) {
        for (int i = 0; i < THREAD_COUNT; i++) {
            threadPool.execute(new Runnable() {
                @Override
                public void run() {
                    try {
                        s.acquire();
                        System.out.println(Thread.currentThread().getName());
                        Thread.sleep(5000);
                        System.out.println("--------------");
                        s.release();
                    } catch (InterruptedException e) {
                    }
                }
            });
        }

        threadPool.shutdown();
    }
}

    b>>计数器,以CountDownLatch为例

import java.util.concurrent.CountDownLatch;

public class CountDownLatchTest2 {
    public static void main(String[] args) {
        // 创建计数器,初始化为2
        final CountDownLatch latch = new CountDownLatch(2);

        new Thread(() -> {
            try {
                System.out.println("子线程"+Thread.currentThread().getName()+"正在执行");
                Thread.sleep(3000);
                System.out.println("子线程"+Thread.currentThread().getName()+"执行完毕");
                latch.countDown();// 减一
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }).start();

        new Thread(() -> {
            try {
                System.out.println("子线程"+Thread.currentThread().getName()+"正在执行");
                Thread.sleep(3000);
                System.out.println("子线程"+Thread.currentThread().getName()+"执行完毕");
                latch.countDown();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }).start();

        try {
            System.out.println("等待2个子线程执行完毕...");
            // 阻塞
            latch.await();
            System.out.println("2个子线程已经执行完毕");
            System.out.println("继续执行主线程");
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

c>>guava RateLimiter    

public void test()
{
    /**
     * 创建一个限流器,设置每秒放置的令牌数:2个。速率是每秒可以2个的消息。
     * 返回的RateLimiter对象可以保证1秒内不会给超过2个令牌,并且是固定速率的放置。达到平滑输出的效果
     */
    RateLimiter r = RateLimiter.create(2);

    while (true)
    {
        /**
         * acquire()获取一个令牌,并且返回这个获取这个令牌所需要的时间。如果桶里没有令牌则等待,直到有令牌。
         * acquire(N)可以获取多个令牌。
         */
        System.out.println(r.acquire());
    }
}

1.2 分布式限流

a>> nginx

limit_req_zone $binary_remote_addr zone=mylimit:10m rate=2r/s;
server {
    location / {
        limit_req zone=mylimit;
    }
}

b>>api-gateway+redis限流

https://github.com/wangzheng0822/ratelimiter4j

2. 熔断对比

功能对比

  Sentinel Hystrix resilience4j
隔离策略 信号量隔离(并发线程数限流) 线程池隔离/信号量隔离 信号量隔离
熔断降级策略 基于响应时间、异常比率、异常数 基于异常比率 基于异常比率、响应时间
实时统计实现 滑动窗口(LeapArray) 滑动窗口(基于 RxJava) Ring Bit Buffer
动态规则配置 支持多种数据源 支持多种数据源 有限支持
扩展性 多个扩展点 插件的形式 接口的形式
基于注解的支持 支持 支持 支持
限流 基于 QPS,支持基于调用关系的限流 有限的支持 Rate Limiter
流量整形 支持预热模式、匀速器模式、预热排队模式 不支持 简单的 Rate Limiter 模式
系统自适应保护 支持 不支持 不支持
控制台 提供开箱即用的控制台,可配置规则、查看秒级监控、机器发现等 简单的监控查看 不提供控制台,可对接其它监控系统

参考文献:

【1】https://mp.weixin.qq.com/s?__biz=MjM5MDE0Mjc4MA==&mid=2651008444&idx=1&sn=a579c3ceb143ea30930bd4c6d4a8d7e2&chksm=bdbed5ef8ac95cf93e71c5393f08e3b97a7e19e8232ce3872231f2cae74f7a19ab15501aeb44&scene=27#wechat_redirect

【2】https://mp.weixin.qq.com/s?__biz=MzIwMzY1OTU1NQ==&mid=2247484306&idx=1&sn=b6c1b7b9d7c57bbb9f82ec451bcda867&chksm=96cd43dea1bacac8a24cde429146f69dba8bb15c5c9c3fe9adfe858d9a4349cc127fbfa84a8c&scene=27#wechat_redirect

【3】https://github.com/alibaba/Sentinel/wiki/Guideline:-%E4%BB%8E-Hystrix-%E8%BF%81%E7%A7%BB%E5%88%B0-Sentinel

原文地址:https://www.cnblogs.com/davidwang456/p/10196191.html

时间: 2024-11-05 16:26:58

分布式系统中的限流与熔断的相关文章

这个注解一次搞定限流与熔断降级:@SentinelResource

在之前的<使用Sentinel实现接口限流>一文中,我们仅依靠引入Spring Cloud Alibaba对Sentinel的整合封装spring-cloud-starter-alibaba-sentinel,就完成了对所有Spring MVC接口的限流控制.然而,在实际应用过程中,我们可能需要限流的层面不仅限于接口.可能对于某个方法的调用限流,对于某个外部资源的调用限流等都希望做到控制.呢么,这个时候我们就不得不手工定义需要限流的资源点,并配置相关的限流策略等内容了. 今天这篇我们就来一起学

Spring Cloud微服务Sentinel+Apollo限流、熔断实战

在Spring Cloud微服务体系中,由于限流熔断组件Hystrix开源版本不在维护,因此国内不少有类似需求的公司已经将眼光转向阿里开源的Sentinel框架.而以下要介绍的正是作者最近两个月的真实项目实践过程,这中间被不少网络Demo示例级别水文误导过,为了以正视听特将实践过程加以总结,希望能够帮到有类似需要的朋友! 一.Sentinel概述 在基于Spring Cloud构建的微服务体系中,服务之间的调用链路会随着系统的演进变得越来越长,这无疑会增加了整个系统的不可靠因素.在并发流量比较高

使用springcloud gateway搭建网关(分流,限流,熔断)

Spring Cloud Gateway Spring Cloud Gateway 是 Spring Cloud 的一个全新项目,该项目是基于 Spring 5.0,Spring Boot 2.0 和 Project Reactor 等技术开发的网关,它旨在为微服务架构提供一种简单有效的统一的 API 路由管理方式. Spring Cloud Gateway 作为 Spring Cloud 生态系统中的网关,目标是替代 Netflix Zuul,其不仅提供统一的路由方式,并且基于 Filter

springboot + aop + Lua分布式限流原理解析

一.什么是限流?为什么要限流?不知道大家有没有做过帝都的地铁,就是进地铁站都要排队的那种,为什么要这样摆长龙转圈圈?答案就是为了 限流 !因为一趟地铁的运力是有限的,一下挤进去太多人会造成站台的拥挤.列车的超载,存在一定的安全隐患.同理,我们的程序也是一样,它处理请求的能力也是有限的,一旦请求多到超出它的处理极限就会崩溃.为了不出现最坏的崩溃情况,只能耽误一下大家进站的时间. 限流是保证系统高可用的重要手段!!! 由于互联网公司的流量巨大,系统上线会做一个流量峰值的评估,尤其是像各种秒杀促销活动

.Net Core的API网关Ocelot的使用(二)[负载,限流,熔断,Header转换]

网关的负载均衡 当下游拥有多个节点的时候,我们可以用DownstreamHostAndPorts来配置 { "UpstreamPathTemplate": "/Api_A/{controller}/{action}", "DownstreamPathTemplate": "/api/{controller}/{action}", "DownstreamScheme": "https",

.Net微服务实践(四)[网关]:Ocelot限流熔断、缓存以及负载均衡

目录 限流 熔断 缓存 Header转化 HTTP方法转换 负载均衡 注入/重写中间件 后台管理 最后 在上篇.Net微服务实践(三)[网关]:Ocelot配置路由和请求聚合中我们介绍了Ocelot的配置,主要特性路由以及服务聚合.接下来,我们会介绍Ocelot的限流.熔断.缓存以及负载均衡. 限流 我们先来看限流的配置 Reroute节点中的配置如下: { "DownstreamPathTemplate": "/api/orders", "Downstr

spring cloud微服务快速教程之(九) Spring Cloud Alibaba--sentinel-限流、熔断降级

0.前言 sentinel的限流.降级功能强大,可以在控制面板中任意制定规则,然后推送到微服务中: 可以根据URL单独制定规则,也可以根据资源名批量制定规则: 需要注意的地方是:1.GITHUB文件在国外的亚马逊服务器已经彻底被墙,无法下载,只能想法找国内的分享,自求多福 2.控制面板制定的规则只保存在内存中,重启就会消失,需要配合其他方式实现持久化存储规则,这点在生产环境中需要注意 1.运行sentinel sentinel只是一个JAR包,下载下来后,直接命令运行该JAR就行,默认的端口是8

网站限流处理

1.常见两种方式 漏桶算法和令牌桶算法 漏桶算法:1.有一个固定容量的漏桶,已固定的速率流出水滴. 2.可以任意速率流入水滴到漏桶 3.当漏桶满了,水溢出(相当于丢弃) 令牌桶算法: 1.以固定的速率向桶里放令牌 2.当桶内的令牌数量达到最大值后,后续放入的令牌被丢弃 3.当需要发送N个单位大小的数据时,就从桶内去N个令牌 4.当桶内的令牌数量小于设定的大小时,不能删除令牌,也就是不能发送数据,这是数据可能被丢弃,也可能被缓冲区缓存下来. 2.其它方式 统计计数,主要思想是记录指定时间内的访问量

Hadoop内部的限流机制

前言 文章标题一開始提及到了一个令人感到有些抽象又显得有些非常"大"的词,限流.事实上这个词语在非常多行业都能够用到,比方近期春运,各大主要城市,火车站,地铁站都要做到限流吧,避免人流量过大造成事故或间接事故,这叫人流量限流,同理也能够用在车流量上.假设基于这个背景,把这里的人群和车辆抽象为数据,对数据进行限流,就是本篇文章的主题了.可能就有人疑惑了,数据为什么要做限流,怎么做限流,有什么优点呢,带着这个疑问,细致的阅读下文的分析吧. 数据的限流 数据的限流更让人理解的称呼应该是&qu