一、前言
在微服务架构中,服务间的相互调用是常态,但网络波动、服务自身故障等因素会导致服务可用性降低。当高并发请求涌入故障服务时,极易引发服务雪崩------ 单个服务故障蔓延至整个调用链路,导致全链路不可用。为解决这一问题,我们需要引入服务容错保护机制,而 Sentinel 作为阿里巴巴开源的流量控制框架,能从流量控制、熔断降级等维度保障服务稳定性。本文将从实战角度,全面讲解 Sentinel 的核心功能与使用方式。
二、高并发场景模拟(服务雪崩雏形)
2.1 环境搭建
2.1.1 服务提供者(sentinel-provider)
-
工程创建 :拷贝 feign_provider 工程,修改应用名为
sentinel-provider -
application.yml 配置:
server:
port: 9090
spring:
cloud:
nacos:
discovery:
server-addr: 192.168.209.129:8848
application:
name: sentinel-provider -
核心服务逻辑(模拟网络延时):
package com.hg.service;
import com.hg.pojo.User;
import org.springframework.stereotype.Service;@Service
public class UserServiceImpl implements UserService {
@Override
public User getUserById(Integer id) {
//模拟网络延时2秒
try {
Thread.sleep(2000);
} catch (InterruptedException e) {
e.printStackTrace();
}
return new User(id,"王粪堆-provider",18);
}
}
2.1.2 Feign 接口工程(sentinel_feign)
- 工程创建:拷贝 feign_interface 工程
- Feign 接口定义:
java
package com.hg.feign;
import com.hg.pojo.User;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
@FeignClient("sentinel-provider")
public interface UserFeign {
@RequestMapping(value = "/provider/getUserById/{id}")
public User getUserById(@PathVariable Integer id);
}
2.1.3 服务消费者(sentinel_consumer)
- 工程创建:拷贝 feign_consumer 工程
- pom.xml 依赖:
xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>springcloud_parent</artifactId>
<groupId>com.hg</groupId>
<version>1.0-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>sentinel_consumer</artifactId>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>com.hg</groupId>
<artifactId>springcloud_common</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<!--feign接口依赖-->
<dependency>
<groupId>com.hg</groupId>
<artifactId>sentinel_feign</artifactId>
<version>1.0-SNAPSHOT</version>
</dependency>
</dependencies>
</project>
- application.yml 配置(限制 Tomcat 最大线程数):
yaml
server:
tomcat:
max-threads: 10 # 默认200,降低线程数放大高并发问题
feign:
client:
config:
default:
connectionTimeout: 5000 # 请求连接超时时间
readTimeout: 5000 # 请求响应超时时间
- 测试接口:
java
@RequestMapping(value = "/hello")
public String hello() {
return "Hello Sentienl!!!";
}
2.2 高并发测试(JMeter)
-
下载 JMeter:https://jmeter.apache.org/

-
创建线程组,设置高并发数;


-
添加 HTTP 请求,访问
http://127.0.0.1:8080/consumer/getUserById/1;

-
同时访问
http://127.0.0.1:8080/consumer/hello,发现 hello 接口出现线程阻塞。
2.3 结论
消费者服务因大量请求堆积,导致非故障接口也无法正常响应,这就是服务雪崩的雏形。而 Sentinel 的核心目标,就是通过流量控制、熔断降级等手段,避免此类问题扩散。

三、Sentinel 核心概念与功能
3.1 什么是 Sentinel
Sentinel(分布式系统的流量防卫兵)是阿里开源的服务保护框架,以流量为切入点,通过流量控制 、熔断降级等能力保障微服务稳定性。
3.2 核心概念
- 资源:Sentinel 要保护的对象,如一个接口、一个方法;
- 规则:保护资源的策略,如流量控制规则、熔断降级规则等。
3.3 核心功能
| 功能 | 作用 |
|---|---|
| 流量控制 | 限制请求流量,避免系统被超出处理能力的请求压垮 |
| 熔断降级 | 当下游服务故障时,暂时切断调用,避免级联失败 |
流量控制
熔断降级
四、Sentinel 快速入门
4.1 方式 1:抛异常式(原生 API)
4.1.1 引入依赖
xml
<!--sentinel核心依赖-->
<dependency>
<groupId>com.alibaba.csp</groupId>
<artifactId>sentinel-core</artifactId>
</dependency>
4.1.2 代码实现
java
@RequestMapping(value = "/hello")
public String hello() {
Entry entry = null;
try {
// 定义受保护的资源
entry = SphU.entry("/consumer/hello");
return "Hello Sentienl!!!";
} catch (BlockException e) {
// 限流/熔断时的兜底逻辑
e.printStackTrace();
return "接口被限流了, exception: " + e;
}finally {
// 释放资源(必须成对出现)
if (entry != null) {
entry.exit();
}
}
}
/**
* 初始化流控规则(@PostConstruct:构造函数执行后初始化)
*/
@PostConstruct
public void initFlowQpsRule() {
List<FlowRule> rules = new ArrayList<>();
FlowRule rule1 = new FlowRule();
rule1.setResource("/consumer/hello"); // 资源名(唯一)
rule1.setGrade(RuleConstant.FLOW_GRADE_QPS); // 限流维度:QPS
rule1.setCount(2); // QPS阈值:2
rules.add(rule1);
FlowRuleManager.loadRules(rules); // 加载规则
}
4.1.3 测试
- 正常访问:返回
Hello Sentienl!!!;
- 高并发访问:触发限流,返回兜底信息。

4.2 方式 2:注解式
4.2.1 引入依赖
xml
<!--sentinel注解依赖-->
<dependency>
<groupId>com.alibaba.csp</groupId>
<artifactId>sentinel-annotation-aspectj</artifactId>
</dependency>
4.2.2 代码实现
- 开启注解支持:
java
@Bean
public SentinelResourceAspect sentinelResourceAspect(){
return new SentinelResourceAspect();
}
- 注解式接口:
java
@RequestMapping(value = "/hello2")
@SentinelResource(value="/consumer/hello2",blockHandler = "blockHandlerMethod")
public String hello2() {
return "Hello Sentienl2!!!";
}
/**
* 限流兜底方法(要求:返回值、参数与原方法一致,最后加BlockException参数)
*/
public String blockHandlerMethod(BlockException e){
return "接口被限流了, exception: " + e;
}
// 初始化规则(同4.1.2,仅修改资源名为/consumer/hello2)
@PostConstruct
public void initFlowQpsRule() {
List<FlowRule> rules = new ArrayList<>();
FlowRule rule1 = new FlowRule();
rule1.setResource("/consumer/hello2");
rule1.setGrade(RuleConstant.FLOW_GRADE_QPS);
rule1.setCount(2);
rules.add(rule1);
FlowRuleManager.loadRules(rules);
}
4.2.3 测试
效果与原生 API 一致,但代码侵入性更低。
4.3 Sentinel 控制台(可视化配置)
4.3.1 控制台安装启动
- 下载控制台 jar 包:https://github.com/alibaba/Sentinel/releases
- 启动命令:
java -jar sentinel-dashboard-1.8.1.jar
- 访问控制台:
http://localhost:8080,默认账号 / 密码:sentinel/sentinel
4.3.2 客户端接入控制台
- 替换依赖:
xml
<!-- 移除原生依赖,引入SpringCloud整合包 -->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>
</dependency>
- application.yml 配置:
yaml
spring:
cloud:
sentinel:
transport:
dashboard: 127.0.0.1:8080 # 控制台地址
- 测试接口:
java
@RequestMapping(value = "/hello3")
public String hello3() {
return "Hello Sentienl3!!!";
}
4.3.3 控制台使用
- 访问
http://127.0.0.1/consumer/hello3(Sentinel 懒加载,需触发接口后控制台才会显示);
- 在控制台配置流控规则,高并发访问即可触发限流。


五、Sentinel 核心规则详解
5.1 流控规则(流量控制)
流控规则用于限制资源的请求流量,核心配置项如下:
| 配置项 | 说明 |
|---|---|
| 资源名 | 唯一标识,默认请求路径 |
| 针对来源 | 限制调用方(微服务名),默认 default(不区分来源) |
| 阈值类型 | QPS(每秒请求数)/ 线程数 |
| 单机阈值 | 限流阈值(如 QPS=2 表示每秒最多 2 次请求) |
| 流控模式 | 直接(限制自身)/ 关联(关联资源阈值触发限流)/ 链路(指定入口限流) |
| 流控效果 | 快速失败(直接拒绝)/Warm Up(预热限流)/ 排队等待(匀速处理) |
5.1.1 阈值类型
- QPS:每秒请求数达到阈值触发限流(适用于短耗时接口);
- 线程数:请求线程数达到阈值触发限流(适用于长耗时接口)。
5.1.2 流控模式
- 直接:默认模式,资源自身达到阈值限流;
- 关联:如 "支付接口" 达到阈值时,限流 "订单接口"(应用让步场景);
- 链路:仅限制从指定接口进入的请求(粒度比 "针对来源" 更细)。
5.1.3 流控效果
- 快速失败:触发限流直接返回异常;
- Warm Up :阈值从
阈值/3开始,预热时长内逐步升至阈值(适用于流量突增场景); - 排队等待:请求匀速通过,超出阈值的请求排队(超时丢弃),适用于削峰填谷。
5.2 热点规则(参数级限流)
热点规则是更细粒度的流控,针对接口参数限流(如限制高频访问的商品 ID / 用户 ID)。
5.2.1 代码实现
java
运行
@RequestMapping(value = "/getUserById/{id}")
@SentinelResource(value = "getUserById", blockHandler = "blockHandlerMethod")
public User getUserById(@PathVariable Integer id) {
return userFeign.getUserById(id);
}
// 兜底方法
public User blockHandlerMethod(Integer id, BlockException e){
return new User(id,"热点参数限流触发",0);
}
5.2.2 控制台配置
配置 "热点规则",指定参数索引、阈值,可设置 "参数例外项"(如 ID=2 时阈值放宽)。
5.3 系统规则(应用级限流)
系统规则针对整个应用限流,粒度粗,慎用!支持 5 种维度:
- LOAD:Linux 系统负载(仅 Linux 生效);
- RT:所有请求平均响应时间;
- 线程数:应用总线程数;
- 入口 QPS:应用所有接口总 QPS;
- CPU 使用率:应用 CPU 占用率。
5.4 授权规则(来源控制)
根据请求来源(origin)做黑白名单控制:
- 实现 RequestOriginParser:解析请求来源(如从参数 / 请求头获取);
java
运行
@Component
public class RequestOriginParserDefinition implements RequestOriginParser {
@Override
public String parseOrigin(HttpServletRequest request) {
// 从参数获取来源标识
return request.getParameter("origin");
}
}
- 控制台配置黑白名单:如黑名单配置 "app1",则 origin=app1 的请求被拒绝。
5.5 降级规则(熔断降级)
当资源出现故障(慢调用 / 异常)时,暂时切断调用,避免级联失败。支持 3 种熔断策略:
表格
| 策略 | 触发条件 |
|---|---|
| 慢调用比例 | 慢调用(超过最大 RT)占比≥阈值,且请求数≥最小请求数 |
| 异常比例 | 异常请求占比≥阈值,且请求数≥最小请求数 |
| 异常数 | 异常请求数≥阈值,且请求数≥最小请求数 |
5.5.1 慢调用比例示例
- 控制台配置:最大 RT=200ms,比例阈值 = 0.5,熔断时长 = 5s,最小请求数 = 5;
- 接口中模拟延时:
Thread.sleep(300);; - 高并发访问触发熔断,5 秒内请求被拒绝,熔断结束后恢复。
六、Sentinel 高级用法
6.1 自定义 blockHandler(兜底逻辑)
6.1.1 同类定义兜底方法
java
运行
@SentinelResource(value ="getUserById", blockHandler="blockHandlerMethod")
public User getUserById(@PathVariable Integer id) {
return userFeign.getUserById(id);
}
// 兜底方法(static修饰,参数需包含原参数+BlockException)
public static User blockHandlerMethod(Integer id, BlockException e) {
return new User(0, "接口被流控/熔断:"+e, 0);
}
6.1.2 外置类定义兜底方法
java
运行
// 外置兜底类
public class BlockHandlerClass {
public static User blockHandlerMethod(Integer id, BlockException e) {
return new User(0, "外置兜底:接口被限流", 0);
}
}
// 接口引用
@SentinelResource(value ="getUserById",
blockHandler="blockHandlerMethod",
blockHandlerClass = BlockHandlerClass.class)
public User getUserById(@PathVariable Integer id) {
return userFeign.getUserById(id);
}
6.2 全局异常处理
默认限流返回 "Blocked by Sentinel (flow limiting)",可实现BlockExceptionHandler自定义返回:
java
运行
@Component
public class GloabBlockExceptionHandler implements BlockExceptionHandler {
@Override
public void handle(HttpServletRequest request, HttpServletResponse response, BlockException e) throws Exception {
response.setContentType("application/json;charset=utf-8");
Result data = null;
if (e instanceof FlowException) {
data = new Result(-1, "限流异常");
} else if (e instanceof DegradeException) {
data = new Result(-2, "降级异常");
}else if (e instanceof ParamFlowException) {
data = new Result(-3, "参数限流异常");
}else if (e instanceof AuthorityException) {
data = new Result(-4, "授权异常");
}else if (e instanceof SystemBlockException) {
data = new Result(-5, "系统负载异常");
}
response.getWriter().write(JSON.toJSONString(data));
}
}
// 统一返回类
class Result {
private int status;
private String msg;
private Object data;
// 构造器、getter/setter省略
}
6.3 Sentinel 整合 Feign
Feign 与 Sentinel 整合,实现远程调用的熔断降级:
- 消费者开启 Feign 支持:
yaml
feign:
sentinel:
enabled: true # 开启Feign熔断
- Feign 接口配置兜底工厂:
java
运行
// 兜底工厂
@Component
public class UserFeignFallback implements FallbackFactory<UserFeign> {
@Override
public UserFeign create(Throwable t) {
return new UserFeign() {
@Override
public User getUserById(Integer id) {
return new User(id,"Feign调用失败:"+t,0);
}
};
}
}
// Feign接口引用兜底工厂
@FeignClient(value="sentinel-provider",fallbackFactory = UserFeignFallback.class)
@RequestMapping(value = "/provider")
public interface UserFeign {
@RequestMapping(value = "/getUserById/{id}")
User getUserById(@PathVariable Integer id);
}
七、总结
Sentinel 作为轻量级的服务容错框架,通过 "资源 + 规则" 的核心设计,提供了流量控制、熔断降级、系统保护等全方位的服务保护能力。相比 Hystrix,Sentinel 更易上手、配置灵活,且支持可视化控制台,是微服务架构中服务容错的优选方案。
在实际应用中,需结合业务场景合理配置规则:
- 流量控制:根据接口 QPS / 线程数设置阈值,选择合适的流控效果;
- 熔断降级:针对慢调用 / 异常请求配置熔断策略,避免级联失败;
- 授权规则:控制请求来源,提升接口安全性;
- 整合 Feign:实现远程调用的熔断兜底,降低服务依赖风险。
通过 Sentinel 的层层防护,可有效避免服务雪崩,保障微服务架构的稳定性。