阿里巴巴开源限流系统 Sentinel 全解析

Sentinel服务限流原理分析 Sentinel(分布式系统的流量防卫兵)是阿里开源的一套用于服务容错的综合性解决方案;Sentinel是面向分布式服务架构的轻量级流量控制组件,主要以流量为切入点,从限流、流量整形、熔断降级、系统负载保护等多个维度来帮助您保障微服务的稳定性;本质要做的就是两件事:①.统计数据:统计某个资源的访问数据(QPS, RT等信息);②.规则判断:判断限流规则, 隔离规则, 降级规则, 熔断规则是否满足;这里的资源。 阅读详情
640?wx_fmt=png

今年下半年阿里开源了自研的限流系统 Sentinel,官方对 Sentinel 的介绍中用到了一系列高大山的名词诸如 限流、熔断降级、流量塑形、系统负载保护等,还有漂亮的形容词诸如 轻巧、专业、实时等。作为技术消费者看到这样的广告词之后禁不住要大声感叹 —— NiuB!更要不得的是 Sentinel 的发布会由阿里的高级技术专家 子衿 主讲,她是一位女性开发者,这在男性主导的中国 IT 产业也算得上难得一见的奇观 —— 也可能是我少见多怪。

640?wx_fmt=png

我花了一整天的时间仔细研究了 Sentinel 的功能和代码,大致摸清了整体的架构和局部的一些技术细节,这里给大家做一次全面的分享。

Sentinel 入门

首先,Sentinel 不算一个特别复杂的系统 ,普通技术开发者也可以轻松理解它的原理和结构。你别看架构图上 Sentinel 的周边是一系列的其它高大山的开源中间件,这不过是一种华丽的包装,其内核 Sentinel Core 确实是非常轻巧的。

首先我们从它的 Hello World 开始,通过深入理解这段入门代码就可以洞悉其架构原理。

<dependency>
    <groupId>com.alibaba.csp</groupId>
    <artifactId>sentinel-core</artifactId>
    <version>1.4.0</version>
</dependency>

640?wx_fmt=png
图片

而分布式则需要另启一个集中的发票服务器,这个服务器针对每个指定的资源每秒只会生成一定量的票数,在执行临界区的代码之前先去集中的发票服务领票,如果领成功了就可以执行,否则就会抛出限流异常。所以分布式限流代价较高,需要多一次网络读写操作。如果读者阅读了我的小册《Redis 深度历险》,里面就提到了 Redis 的限流模块,Sentinel 限流的原理和它是类似的,只不过 Sentinel 的发票服务器是自研的,使用了 Netty 框架。

Sentinel 在使用上提供了两种形式,一种是异常捕获形式,一种是布尔形式。也就是当限流被触发时,是抛出异常来还是返回一个 false。下面我们看看它的异常捕获形式,这是单机版

import com.alibaba.csp.sentinel.Entry;
import com.alibaba.csp.sentinel.SphU;
import com.alibaba.csp.sentinel.slots.block.BlockException;

public class SentinelTest {
    public static void main(String[] args) {
        // 配置规则
        List<FlowRule> rules = new ArrayList<>();
        FlowRule rule = new FlowRule();
        rule.setResource("tutorial");
        // QPS 不得超出 1
        rule.setCount(1);
        rule.setGrade(RuleConstant.FLOW_GRADE_QPS);
        rule.setLimitApp("default");
        rules.add(rule);
        // 加载规则
        FlowRuleManager.loadRules(rules);
        // 下面开始运行被限流作用域保护的代码
        while (true) {
            Entry entry = null;
            try {
                entry = SphU.entry("tutorial");
                System.out.println("hello world");
            } catch (BlockException e) {
                System.out.println("blocked");
            } finally {
                if (entry != null) {
                    entry.exit();
                }
            }
            try {
                Thread.sleep(500);
            } catch (InterruptedException e) {}
        }
    }
}

INFO: log base dir is: /Users/qianwp/logs/csp/
INFO: log name use pid is: false
hello world
blocked
hello world
blocked
hello world
blocked
hello world
blocked
...

我们再看看它的 bool 形式,使用也是很简单,大同小异。

import java.util.ArrayList;
import java.util.List;
import com.alibaba.csp.sentinel.SphO;
import com.alibaba.csp.sentinel.slots.block.RuleConstant;
import com.alibaba.csp.sentinel.slots.block.flow.FlowRule;
import com.alibaba.csp.sentinel.slots.block.flow.FlowRuleManager;

public class SentinelTest {
    public static void main(String[] args) {
        // 配置规则
        List<FlowRule> rules = new ArrayList<>();
        FlowRule rule = new FlowRule();
        rule.setResource("tutorial");
        // QPS 不得超出 1
        rule.setCount(1);
        rule.setGrade(RuleConstant.FLOW_GRADE_QPS);
        rule.setLimitApp("default");
        rules.add(rule);
        FlowRuleManager.loadRules(rules);
        // 运行被限流作用域保护的代码
        while (true) {
            if (SphO.entry("tutorial")) {
                try {
                    System.out.println("hello world");
                } finally {
                    SphO.exit();
                }
            } else {
                System.out.println("blocked");
            }
            try {
                Thread.sleep(500);
            } catch (InterruptedException e) {}
        }
    }
}

规则控制

上面的例子中规则都是通过代码写死的,在实际的项目中,规则应该需要支持动态配置。这就需要有一个规则配置源,它可以是 Redis、Zookeeper 等数据库,还需要有一个规则变更通知机制和规则配置后台,允许管理人员可以在后台动态配置规则并实时下发到业务服务器进行控制。

640?wx_fmt=png

有一些规则源存储不支持事件通知机制,比如关系数据库,Sentinel 也提供了定时刷新规则,比如每隔几秒来刷新内存里面的限流规则。下面是 redis 规则源定义

// redis 地址
RedisConnectionConfig redisConf = new RedisConnectionConfig("localhost", 6379, 1000);
// 反序列化算法
Converter<String, List<FlowRule>> converter = r -> JSON.parseArray(r, FlowRule.class);
// 定义规则源,包含全量和增量部分
// 全量是一个字符串key,增量是 pubsub channel key
ReadableDataSource<String, List<FlowRule>> redisDataSource = new RedisDataSource<List<FlowRule>>(redisConf,"app_key", "app_pubsub_key", converter);
FlowRuleManager.register2Property(redisDataSource.getProperty());

健康状态上报与检查

接入 Sentinel 的应用服务器需要将自己的限流状态上报到 Dashboard,这样就可以在后台实时呈现所有服务的限流状态。Sentinel 使用拉模型来上报状态,它在当前进程注册了一个 HTTP 服务,Dashboard 会定时来访问这个 HTTP 服务来获取每个服务进程的健康状况和限流信息。

640?wx_fmt=png

Sentinel 需要将服务的地址以心跳包的形式上报给 Dashboard,如此 Dashboard 才知道每个服务进程的 HTTP 健康服务的具体地址。如果进程下线了,心跳包就停止了,那么对应的地址信息也会过期,如此Dashboard 就能准实时知道当前的有效进程服务列表。

当前版本开源的 Dashboard 不具备持久化能力,当管理员在后台修改了规则时,它会直接通过 HTTP 健康服务地址来同步服务限流规则直接控制具体服务进程。如果应用重启,规则将自动重置。如果你希望通过 Redis 来持久化规则源,那就需要自己定制 Dashboard。定制不难,实现它内置的持久化接口即可。

分布式限流

前面我们说到分布式限流需要另起一个 Ticket Server,由它来分发 Ticket,能够获取到 Ticket 的请求才可以允许执行临界区代码,Ticket 服务器也需要提供规则输入源。

640?wx_fmt=png

Ticket Server 是单点的,如果 Ticket Server 挂掉了,应用服务器限流将自动退化为本地模式。

框架适配

Sentinel 保护的临界区是代码块,通过拓展临界区的边界就可以直接适配各种框架,比如 Dubbo、SpringBoot 、GRPC 和消息队列等。每一种框架的适配器会在请求边界处统一定义临界区作用域,用户就可以完全不必手工添加熔断保护性代码,在毫无感知的情况下就自动植入了限流保护功能。

熔断降级

限流在于限制流量,也就是 QPS 或者线程的并发数,还有一种情况是请求处理不稳定或者服务损坏,导致请求处理时间过长或者老是频繁抛出异常,这时就需要对服务进行降级处理。所谓的降级处理和限流处理在形式上没有明显差异,也是以同样的形式定义一个临界区,区别是需要对抛出来的异常需要进行统计,这样才可以知道请求异常的频率,有了这个指标才会触发降级。

// 定义降级规则
List<DegradeRule> rules = new ArrayList<>();
DegradeRule rule = new DegradeRule();
rule.setResource("tutorial");
// 5s内异常不得超出10
rule.setCount(10);
rule.setGrade(RuleConstant.DEGRADE_GRADE_EXCEPTION_COUNT);
rule.setLimitApp("default");
rules.add(rule);
DegradeRuleManager.loadRules(rules);

Entry entry = null;
try {
  entry = SphU.entry(key);
  // 业务代码在这里
} catch (Throwable t) {
  // 记录异常
  if (!BlockException.isBlockException(t)) {
    Tracer.trace(t);
  }
} finally {
  if (entry != null) {
    entry.exit();
  }
}

热点限流

还有一种特殊的动态限流规则,用于限制动态的热点资源。内部采用 LRU 算法计算出 topn 热点资源,然后对 topn 的资源进行限流,同时还提供特殊资源特殊对待的参数设置。

640?wx_fmt=png
图片
ParamFlowRule ruleUser = new ParamFlowRule();
// 同样的 userId QPS 不得超过 10
ruleUser.setParamIdx(0).setCount(10);
// qianwp用户特殊对待,QPS 上限是 100
ParamFlowItem uitem = new ParamFlowItem("qianwp", 100, String.class);
ruleUser.setParamFlowItemList(Collections.singletonList(uitem));

ParamFlowRule ruleBook = new ParamFlowRule();
// 同样的 bookId QPS 不得超过 20
ruleBook.setParamIdx(1).setCount(20);
// redis 的书特殊对待,QPS 上限是 100
ParamFlowItem bitem = new ParamFlowItem("redis", 100, String.class);
ruleBook.setParamFlowItemList(Collections.singletonList(item));

// 加载规则
List<ParamFlowRule> rules = new ArrayList<>();
rules.add(ruleUser);
rules.add(ruleBook);
ParamFlowRuleManager.loadRules(rules);

// userId的用户访问bookId的书
Entry entry = Sphu.entry(key, EntryType.IN, 1, userId, bookId);

系统自适应限流 —— 过载保护

当系统的负载较高时,为了避免系统被洪水般的请求冲垮,需要对当前的系统进行限流保护。保护的方式是逐步限制 QPS,观察到系统负载恢复后,再逐渐放开 QPS,如果系统的负载又下降了,就再逐步降低 QPS。如此达到一种动态的平衡,这里面涉及到一个特殊的保持平衡的算法。系统的负载指数存在一个问题,它取自操作系统负载的 load1 参数,load1 参数更新的实时性不足,从 load1 超标到恢复的过程存在一个较长的过渡时间,如果使用一刀切方案,在这段恢复时间内阻止任何请求,待 load1 恢复后又立即放开请求,势必会导致负载的大起大落,服务处理的时断时开。为此作者将 TCP 拥塞控制算法的思想移植到这里实现了系统平滑的过载保护功能。这个算法很精巧,代码实现并不复杂,效果却是非常显著。

算法定义了一个稳态公式,稳态一旦打破,系统负载就会出现波动。算法的本质就是当稳态被打破时,通过持续调整相关参数来重新建立稳态。

640?wx_fmt=jpeg
图片

稳态公式很简单:ThreadNum * (1/ResponseTime) = QPS,这个公式很好理解,就是系统的 QPS 等于线程数乘以单个线程每秒可以执行的请求数量。系统会实时采样统计所有临界区的 QPS 和 ResponseTime,就可以计算出相应的稳态并发线程数。当负载超标时,通过判定当前的线程数是否超出稳态线程数就可以明确是否需要拒绝当前的请求。

定义自适应限流规则需要提供多个参数

  1. 系统的负载水平线,超过这个值时触发过载保护功能

  2. 当过载保护超标时,允许的最大线程数、最长响应时间和最大 QPS,可以不设置

List<SystemRule> rules = new ArrayList<SystemRule>();
SystemRule rule = new SystemRule();
rule.setHighestSystemLoad(3.0);
rule.setAvgRt(10);
rule.setQps(20);
rule.setMaxThread(10);
rules.add(rule);
SystemRuleManager.loadRules(Collections.singletonList(rule));

640?wx_fmt=png

大拇指长按图片识别二维码,阅读更多深度内容

Spring Cloud Alibaba 第二篇(Sentinel、Sleuth、Gateway组件) Spring Cloud Gateway 是 Spring 官方基于 Spring 5.0,Spring Boot 2.0 和 Project Reactor 等技术开发的网关,Spring Cloud Gateway 旨在为微服务架构提供一种简单而有效的统一的 API 路由管理方式。Spring Cloud Gateway 作为 Spring Cloud 生态系中的网关,目标是替代 Netflix ZUUL。 阅读详情

相关推荐

SpringCloud Sentinel 服务保护完整教程

《Sentinel流量控制与系统保护全解析》 摘要: 本文全面介绍了阿里巴巴开源的分布式系统防护组件Sentinel,涵盖其核心功能、实现原理和实际应用。主要内容包括: 核心功能模块:流量控制、熔断降级、系统保护,支持多种限流模式和策略(QPS/线程数、直接/关联/链路模式、快速失败/WarmUp/排队等待)。 特色功能实现: 热点参数限流:针对特定参数值(如商品ID)精细化控制 集群流控:通过TokenServer协调分布式环境流量 规则持久化:支持Nacos/Apollo等多种数据源 最佳实践应用: 微

weixin_51040479的博客 1012

Sentinel 限流原理

Sentinel 限流原理 并发线程数 QPS

杨宇昌的博客 2万+

Sentinel 1.7.0可视化监控界面配置指南:从下载到登录的全流程解析

本文详细解析了Sentinel 1.7.0可视化监控界面的配置流程,从下载、安装到登录的全过程。通过环境准备、控制台部署、启动参数配置等步骤,帮助开发者快速搭建高效的微服务监控系统,提升系统稳定性与可靠性。

weixin_29204205的博客 574

SpringCloud Alibaba - Sentinel篇

Sentinel是阿里巴巴开源的一款微服务流量治理组件,主要以流量为切入点,从流量限流、熔断降级、系统负载保护等多个维度来帮助开发者保障微服务的稳定性。

白豆五的博客 1万+

EBS开发_离散工单创建API

--以下代码于20171213在TONY环境中实现 DECLARE     l_iface_rec    wip.wip_job_schedule_interface%ROWTYPE; --工单任务接口表     l_group_id     NUMBER;     l_returnstatus VARCHAR2(40);     l_errormsg     VARCHAR2(2000

蜗牛先生快跑的博客 2596

保姆级教程:不用看古早代码,5分钟搞懂泛微ecology9附件存储与接口调用

本文详细解析了泛微ecology9附件存储与接口调用的核心原理,提供从基础概念到实战操作的完整指南。通过拆解文档化附件设计理念、解析RESTful接口参数,并给出Python代码示例,帮助开发者快速掌握附件上传与业务集成的关键技巧,提升二次开发效率。

weixin_28688385的博客 351

1命名规则 sentinel_阿里巴巴开源限流系统 Sentinel 全解析

今年下半年阿里开源了自研的限流系统 Sentinel,官方对 Sentinel 的介绍中用到了一系列高大山的名词诸如 限流、熔断降级、流量塑形、系统负载保护等,还有漂亮的形容词诸如 轻巧、专业、实时等。作为技术消费者看到这样的广告词之后禁不住要大声感叹 —— NiuB!更要不得的是 Sentinel 的发布会由阿里的高级技术专家 子衿 主讲,她是一位女性开发者,这在男性主导额 IT 产业也算得上难...

weixin_39974400的博客 154

关键词‖旋变传感器

旋转变压器(以下简称旋变)安装在永磁同步驱动电机的非传动端,其作用是检测转子的位置和速度。目前,通常采采用结构简单、坚固耐用、环境适应性好的磁阻式旋变作为位置传感器。

m0_72345077的博客 2154

sentinel 阿里 原理_阿里巴巴开源限流系统 Sentinel 全解析

今年下半年阿里开源了自研的限流系统 Sentinel,官方对 Sentinel 的介绍中用到了一系列高大山的名词诸如 限流、熔断降级、流量塑形、系统负载保护等,还有漂亮的形容词诸如 轻巧、专业、实时等。作为技术消费者看到这样的广告词之后禁不住要大声感叹 —— NiuB!更要不得的是 Sentinel 的发布会由阿里的高级技术专家 子衿 主讲,她是一位女性开发者,这在男性主导额 IT 产业也算得上难...

weixin_39808143的博客 245

C++实战:基于ONNX Runtime与OpenCV部署XFeat图像匹配模型

本文详细介绍了在C++环境中,利用ONNX Runtime与OpenCV高效部署XFeat图像匹配模型的完整流程。内容涵盖环境搭建、模型转换、核心代码封装及可视化实现,旨在帮助开发者将这一先进的深度学习模型集成到对性能要求苛刻的工业或嵌入式应用中,实现鲁棒且快速的特征匹配。

gpu4optimizer的博客 522

C#构建高精度预测模型:从数据预处理到模型部署的实战指南

【代码】C#构建高精度预测模型:从数据预处理到模型部署的实战指南。

墨夶的博客 1266

Sentinel 学习笔记

Sentinel 学习笔记 文章目录Sentinel 学习笔记1. 简介2. 依赖3. 限流(FlowRule)4. 熔断降级(DegradeRule)5. 限流和熔断降级的区别6. 参考资料 1. 简介 Sentinel是阿里巴巴自研的限流熔断系统。 2. 依赖 <dependency> <groupId>com.alibaba.csp</groupId> <artifactId>sentinel-core</artifactId&gt

WLFIGHTER的专栏 286

【温室气体】GOSAT 数据产品

【温室气体】GOSAT 数据产品

WW、forever的博客 238

深入学习SpringCloud Alibaba微服务架构,揭秘Nacos、Sentinel、Seata等核心技术,助力构建高效系统!

📚【第01阶段】课程简介:全面介绍课程内容,为你提供学习引导和目标规划,让你快速进入学习状态!💡🔍【第02阶段】基于SpringCloud Alibaba的微服务电商解决方案 试看:探索在电商领域如何应用SpringCloud Alibaba打造强大的微服务架构,助你对解决方案有更清晰的认识!🛍️🔧【第03阶段】Nacos Config 如何动态切换的开发环境 试看:深入了解Nacos Config的特性,学习如何实现动态环境切换,为你构建灵活的开发环境!⚙️。

qwert 1714

万字长文带你由浅入深夯实ARM汇编基础——汇编指令及寻址方式最全梳理(附示例)!

见到汇编就害怕?读完这篇,扫除汇编拦路虎!!(示例丰富,可做手册,随手查阅!)

车载系统攻城狮 1万+

【AI大模型应用开发】3.2 RAG实战 - RAG应用+UI实现加载本地文件并对话

前面我们实现了RAG基本流程,今天我们在此基础上给它加个UI界面,在浏览器打开,实现上传本地文件、解析,并用大模型实现与该文档的对话。也就是一个阉割版demo版的ChatPDF或知识库对话系统。

同学小张的博客 3056

微服务容错三剑客:深度解析Sentinel、Hystrix与Resilience4j的实战选型

本文深度解析微服务容错领域的三大框架:Sentinel、Hystrix与Resilience4j,通过电商秒杀等实战场景对比其核心特性与适用场景。重点探讨断路器模式在防止系统雪崩中的关键作用,并提供选型建议与配置优化技巧,帮助开发者构建高可用的微服务架构。

weixin_29267307的博客 378

ET2012新版免狗免安装绿色软件

ET2012新版免狗免安祖昂绿色软件。,新界面,新视觉,

Spring Security- 接口访问频率限制的实现

Spring Security 接口访问频率限制实现指南 本文介绍如何在Spring Security中实现接口访问频率限制功能,保护系统免受暴力破解和恶意请求攻击。 核心实现方案 基于Redis的滑动窗口算法:使用Redis存储请求计数和时间戳,保证分布式环境下的一致性 自定义过滤器:通过OncePerRequestFilter拦截请求并执行限流检查 灵活配置:支持按用户/IP/接口等多维度配置限流规则 主要技术组件 Spring Security过滤器链 Redis原子操作(INCR+EXPIRE) 自

千淘万漉虽辛苦,吹尽狂沙始到金 1万+

jdk-8u144-linux-x64.tar.gz.

该资源为搭建Linux系统Java环境用,资源的后缀为tar.gz格式的压缩包

蓝牙模块HM-10手册

蓝牙模块HM-10手册,该手册对蓝牙模块HM-10进行了详细的介绍和使用方法以及一些AT指令。

一文带你彻底搞懂阿里巴巴开源组件Sentinel!

Sentinel诞生于2012年,当时主要用于入口流量控制。经过几年的发展及其在阿里巴巴集团内部的生产实践,Sentinel基本上已经覆盖了阿里巴巴内部的所有核心业务场景。2018年,Sentinel进行了开源,2019年推出了C++版本,2020年推出了Go语言版本。在Sentinel中有两个基本概念:资源和限流规则。其中,资源是最关键的,Sentinel最终要保护的就是资源。资源可以是应用程序中的任何内容,如由应用程序提供的接口,或由应用程序调用的其他第三方提供的服务,也可以是一段代码或一个方法等。

程序员高级码农的博客 1657

怀旧版电脑GBC模拟器

再现原版GBC掌机的界面,电脑运行连游戏界面都一样大小,很怀旧,很真实,(英文版)强烈推荐,很小的文件,很难才找到的。

深度解析阿里的Sentinel

这是《Spring Cloud 进阶》专栏的第五篇文章,这篇文章介绍一下阿里开源的流量防卫兵Sentinel,一款非常优秀的开源项目,经过近10年的双十一的考验,非常成熟的一款产品。sentinel顾名思义:卫兵;在Redis中叫做哨兵,用于监控主从切换,但是在微服务中叫做流量防卫兵。Sentinel 以流量为切入点,从流量控制熔断降级系统负载保护等多个维度保护服务的稳定性。丰富的应用场景:Sentinel 承接了阿里巴巴近 10 年的双十一。

BUG指挥课堂 3416
上一篇: 一位 40 岁老程序员的反思
下一篇: 滴滴工程师图文并茂带你深入理解 TCP 握手分手全过程
码洞
博客等级 码龄10年 41粉丝 137原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值