第四次课:基于Sentinel的服务限流及熔断

飞一样的编程
飞一样的编程
擅长邻域:Java,MySQL,Linux,nginx,springboot,mongodb,微信小程序,vue

分类: springboot 专栏: 新版springcloud分布式学习 标签: 限流和熔断

2024-04-27 10:16:47 700浏览

基于Sentinel的服务限流及熔断

Sentinel简介

Sentinel是阿里巴巴出品的面向分布式服务架构的轻量级流量控制组件,主要以流量为切入点,从限流、流量整形、熔断降级、系统负载保护等多个维度来保障微服务的稳定性。

主页地址: https://sentinelguard.io/zh-cn/docs/introduction.html

资源级别做限流

什么是限流:拿旅游景点举例子

针对某个微服务的某个接口,属于资源级别的限流

基本使用

依赖

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

定义资源——抛出异常的方式

  // 1.5.0 版本开始可以直接利用 try-with-resources 特性
        try (Entry entry = SphU.entry("storge")) {
            // 被保护的逻辑
            //商品id和数量  这里就只模拟了 业务代码省略
            return "success";
        } catch (BlockException ex) {
            // 处理被流控的逻辑
            return "系统繁忙,请稍后重试";
        }

定义规则-编码方式

 //定义规则每秒最多只能通过 2个请求。
    @PostConstruct
    private static void initFlowRules(){
        List<FlowRule> rules = new ArrayList<>();
        FlowRule rule = new FlowRule();
        rule.setResource("storge");
        rule.setGrade(RuleConstant.FLOW_GRADE_QPS);
        // Set limit QPS to 2
        rule.setCount(2);
        rules.add(rule);
        FlowRuleManager.loadRules(rules);
    }

定义规则-sentinel控制台操作

https://github.com/alibaba/Sentinel/

去下载控制台jar,然后启动项目

java -Dserver.port=9000  -jar sentinel-dashboard-1.8.7.jar

让微服务项目跟sentinel关联起来

<dependency>
    <groupId>com.alibaba.csp</groupId>
    <artifactId>sentinel-transport-simple-http</artifactId>
    <version>1.8.7</version>
</dependency>
# 设置sentinel控制台的主机地址和端口
-Dcsp.sentinel.dashboard.server=localhost:9000
# 设置本地应用在sentinel控制台中的名称
-Dproject.name=StrogeSentinel

页面上新建流控规则

定义资源——返回布尔值的方式

SphO 提供 if-else 风格的 API。用这种方式,当资源发生了限流之后会返回 false,这个时候可以根据返回值,进行限流之后的逻辑处理。示例代码如下:

 // 资源名可使用任意有业务语义的字符串
  if (SphO.entry("自定义资源名")) {
    // 务必保证finally会被执行
    try {
      /**
      * 被保护的业务逻辑
      */
    } finally {
      SphO.exit();
    }
  } else {
    // 资源访问阻止,被限流或被降级
    // 进行相应的处理操作
  }

定义资源——异步调用的方式

Sentinel 支持异步调用链路的统计。在异步调用中,需要通过 SphU.asyncEntry(xxx) 方法定义资源,并通常需要在异步的回调函数中调用 exit 方法。以下是一个简单的示例:

try {
    AsyncEntry entry = SphU.asyncEntry(resourceName);

    // 异步调用.
    doAsync(userId, result -> {
        try {
            // 在此处处理异步调用的结果.
        } finally {
            // 在回调结束后 exit.
            entry.exit();
        }
    });
} catch (BlockException ex) {
    // Request blocked.
    // Handle the exception (e.g. retry or fallback).
}

写一个异步调用接口的步骤

@EnableAsync
public class StorgeApp {
@Async
    String  doAsync(){
        return "success";
    }


    @GetMapping
    public String  updateStorge(){
        try {
            AsyncEntry entry = SphU.asyncEntry("storge3");


                try {
                    // 在此处处理异步调用的结果.
                   return  doAsync();

                } finally {
                    // 在回调结束后 exit.
                    entry.exit();
                }
        } catch (BlockException ex) {
            return "系统繁忙,请稍后重试";
        }

    }

定义资源——注解的方式

Sentinel 支持通过 @SentinelResource 注解定义资源并配置 blockHandler 和 fallback 函数来进行限流之后的处理。示例:

<dependency>
    <groupId>com.alibaba.csp</groupId>
    <artifactId>sentinel-annotation-aspectj</artifactId>
    <version>x.y.z</version>
</dependency>

@Configuration
public class SentinelAspectConfiguration {

    @Bean
    public SentinelResourceAspect sentinelResourceAspect() {
        return new SentinelResourceAspect();
    }
}

    @GetMapping
    @SentinelResource(value = "storge4",blockHandler = "handler")
    public String  updateStorge(){
        return "success";
    }
    public String handler(BlockException e){
        e.printStackTrace();
        return "系统繁忙,请稍后重试";
    }

整合springcloud-alibaba

<!-- https://mvnrepository.com/artifact/com.alibaba.cloud/spring-cloud-starter-alibaba-sentinel -->
<dependency>
    <groupId>com.alibaba.cloud</groupId>
    <artifactId>spring-cloud-starter-alibaba-sentinel</artifactId>
    <version>2022.0.0.0-RC1</version>
</dependency>
@RestController
@RequestMapping("/stroge")
public class StrogeController {
    @GetMapping
    @SentinelResource(value = "storge",blockHandler = "storgeBlockHandler")
    public String update(){

        return "success";
    }


    String storgeBlockHandler(BlockException e){
        e.printStackTrace();
        return "系统繁忙,请稍后重试";

    }
}
spring:
  application:
    name: storge-service
  cloud:
    sentinel:
      transport:
        dashboard: localhost:9000

资源级别熔断机制

针对某个微服务的某个接口,属于资源级别的

平均响应时间rt ,这里设置时间短一点便于测试

编码实现

@PostConstruct
    public void initRule(){
        List<DegradeRule> rules = new ArrayList<>();
        DegradeRule rule = new DegradeRule();
        rule.setResource("storge2");
        rule.setGrade(RuleConstant.DEGRADE_GRADE_RT);
        // 定义阈值
        rule.setCount(0.01);
        rule.setTimeWindow(10);
        rules.add(rule);
        DegradeRuleManager.loadRules(rules);
    }

页面操作

  • 最大RT:Response Time 响应时间,超过时间则为慢调用
  • 比例阈值:当服务请求数超过最小请求数,那么在统计时长里,如果策略为慢调用比例,那么慢调用占全部请求数的比例超过或等于比例阈值(慢调用/全部请求数),那么就会触发熔断,阈值范围为[0.0,1.0]代表 0% - 100%,如果为0.5则是慢调用占全部请求数的比例为50%或以上则触发熔断。
  • 熔断时长:顾名思义,就是触发熔断后,熔断持续的时长。经过熔断时长后熔断器会进入探测恢复状态(HALF-OPEN 状态),若接下来的一个请求响应时间小于设置的慢调用 RT 则结束熔断,若大于设置的慢调用 RT 则会再次被熔断。
  • 最小请求数:熔断触发的最小请求数,请求数小于该值时即使异常比率超出阈值也不会熔断。
  • 统计时长:即在设定的时间内进行统计。

参考文章:https://www.cnblogs.com/Alickx/articles/15298401.html

系统级别的保护机制

Sentinel 系统自适应保护从整体维度对应用入口流量进行控制,结合应用的 Load、总体平均 RT、入口 QPS 和线程数等几个维度的监控指标,让系统的入口流量和系统的负载达到一个平衡,让系统尽可能跑在最大吞吐量的同时保证系统整体的稳定性。

其实是针对整个微服务

@RestController
@RequestMapping("/storge3")
public class StorgeController3 {
    @GetMapping
    @SentinelResource(entryType = EntryType.IN)
    public String hello(){

        return "success";
    }

}

出现的问题:系统规则配置添加后没效

https://developer.aliyun.com/ask/570903

可以改用低版本的试试

补充:

各种整合

sentinel整合RestTemplate,也可以整合springcloud 整合后面要学习的Feign,整合gateway网关等。以及sentinel数据持久化。这些就自行学习

熔断和降级的区别

降级(Degradation)降低级别的意思,它是指程序在出现问题时,仍能保证有限功能可用的一种机制。

比如电商交易系统在双 11 时,使用的人比较多,此时如果开放所有功能,可能会导致系统不可用,所以此时可以开启降级功能,优先保证支付功能可用,而其他非核心功能,如评论、物流、商品介绍等功能可以暂时关闭。

所以,从上述信息可以看出:降级是一种退而求其次的选择,而熔断却是整体不可用。

好博客就要一起分享哦!分享海报

此处可发布评论

评论(0展开评论

暂无评论,快来写一下吧

展开评论

您可能感兴趣的博客

客服QQ 1913284695