springCloudAlibaba之服务熔断组件---sentinel

sentinel组件学习

sentinel学习

  • 服务雪崩

服务雪崩效应:因服务提供者的不可用导致服务调用者的不可用,并将不可用逐渐放大的过程。

sentinel容错机制

常见的容错机制有超时机制、服务限流、隔离、服务熔断

  • 超时机制
    在不做任何处理的情况下,服务提供者不可用回导致消费者请求线程强制等待,而造成系统资源耗尽。加入超时机制,一旦超时,就释放资源。由于释放资源较快,一定程度上可以抑制资源耗尽的问题。
  • 服务限流
    某个服务达到QPS设定最大值则抛异常。
  • 服务熔断
  • 服务降级
    有服务熔断,必然要有服务降级。
    所谓降级,就是当某个服务熔断之后,服务将不再被调用,此时客户端可以自己准备一个本地的fellback(回退),回调,返回一个缺省值。例如:(备用接口/缓存/mock数据),这样做,虽然服务水平下降,但好歹可用,比直接挂掉要强,当然这也要看适合的业务场景。(服务熔断之后进入客户端降级方法)

使用代码方式进行QPS流控-流控规则初体验

  • 引入sentinel相关包
xml 复制代码
  <dependencies>
    <dependency>
      <groupId>org.springframework.boot</groupId>
      <artifactId>spring-boot-starter-web</artifactId>
    </dependency>

    <!--sentinel核心库-->
    <dependency>
      <groupId>com.alibaba.csp</groupId>
      <artifactId>sentinel-core</artifactId>
      <version>1.8.0</version>
    </dependency>

    <dependency>
      <groupId>org.projectlombok</groupId>
      <artifactId>lombok</artifactId>
    </dependency>

    <!--sentinel注解方式-->
    <dependency>
      <groupId>com.alibaba.csp</groupId>
      <artifactId>sentinel-annotation-aspectj</artifactId>
      <version>1.8.0</version>
    </dependency>

    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>3.8.1</version>
      <scope>test</scope>
    </dependency>

    <!--sentinel整合dashbaord控制台-->
    <dependency>
      <groupId>com.alibaba.csp</groupId>
      <artifactId>sentinel-transport-simple-http</artifactId>
      <version>1.8.0</version>
    </dependency>
  </dependencies>
  • 代码实现
java 复制代码
package com.sentinel.controller;

import com.alibaba.csp.sentinel.Entry;
import com.alibaba.csp.sentinel.SphU;
import com.alibaba.csp.sentinel.Tracer;
import com.alibaba.csp.sentinel.slots.block.BlockException;
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;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.annotation.PostConstruct;
import java.util.ArrayList;
import java.util.List;

/**
 * @author : zhouzhiqiang
 * @date : 2024/6/5 23:25
 * @description :
 */
@Slf4j
@RestController
@RequestMapping("/hello")
public class HelloController {

    private static final String RESOURCE_NAME="hello";
    private static final String USER_RESOURCE_NAME="user";
    private static final String DEGRADE_RESOURCE_NAME="degrade";

    @RequestMapping("/helloSentinel")
    public String hello(){

        Entry entry=null;
        try {
            entry= SphU.entry(RESOURCE_NAME);
            String str="hello world";
            log.info("======="+str+"=======");
            return str;
        } catch (BlockException e) {
            log.info("block");
            return "被限流了!";
        }catch (Exception e){
            Tracer.traceEntry(e,entry);
        }finally {
            if (entry != null) {
                entry.exit();
            }
        }
        return null;
    }

    @PostConstruct
    public static void initFlowRules(){
        //流控规则
        List<FlowRule> rules=new ArrayList<>();

        //流控
        FlowRule rule = new FlowRule();
        //为哪个资源进行流量控制
        rule.setResource(RESOURCE_NAME);
        rule.setGrade(RuleConstant.FLOW_GRADE_QPS);
        rule.setCount(1);
        rules.add(rule);

        //加载流控规则
        FlowRuleManager.loadRules(rules);
    }
}

使用@SentinelResource注解进行流控

要使用这个注解需要引入相关包和配置SentinelResourceAspect的bean

  • 引入包
xml 复制代码
    <dependency>
      <groupId>com.alibaba.csp</groupId>
      <artifactId>sentinel-annotation-aspectj</artifactId>
      <version>1.8.0</version>
    </dependency>
  • 配置bean
java 复制代码
  @Bean
    public SentinelResourceAspect sentinelResourceAspect(){
        return new SentinelResourceAspect();
    }
  • 使用注解方式

value:定义资源(接口名称)

blockHandler :设置流控降级后的处理方法,默认该方法,必须声明在一个类中

fallback:接口中出现异常了,就可以交给fellback指定的处理方法

java 复制代码
@PostConstruct
    public static void initFlowRules(){
        //流控规则
        List<FlowRule> rules=new ArrayList<>();

        //流控
        FlowRule rule = new FlowRule();
        //为哪个资源进行流量控制
        rule.setResource(USER_RESOURCE_NAME);
        rule.setGrade(RuleConstant.FLOW_GRADE_QPS);
        rule.setCount(1);
        rules.add(rule);

        //加载流控规则
        FlowRuleManager.loadRules(rules);
    }

    @RequestMapping("/user")
    @SentinelResource(value = USER_RESOURCE_NAME,blockHandler = "blockHandlerForGetUser",fallback = )
    public User getUser(String id){
        return new User("zzq");
    }

    /**
     * 注意:
     * 1、一定是public
     * 2、返回值一定得和原方法返回值一致,包含方法的参数
     * 3、可以在参数的最后添加BlockException,可以区分是什么规则的处理方法
     * @param id
     * @param e
     * @return
     */
    //降级方法
    public User blockHandlerForGetUser(String id,BlockException e){
        e.printStackTrace();
        return new User("被流控了!");
    }

通过代码方式设置降级规则-降级规则初体验

java 复制代码
@RestController
@RequestMapping("/test")
public class TestController {

    private static final String DEGRADE_RESOURCE_NAME="degrade";

    @RequestMapping("/degrade")
    @SentinelResource(value = DEGRADE_RESOURCE_NAME,entryType = EntryType.IN,blockHandler = "blockHandlerForJob")
    public User degrade(String id){
        int i=1;
        int sum=i/0;
        return new User("成功");
    }

    public User blockHandlerForJob(String id, BlockException e){
        e.printStackTrace();
        return new User("触发降级规则");
    }

    @PostConstruct
    public void initDegradeRule(){
        List<DegradeRule> rules=new ArrayList<>();

        DegradeRule rule = new DegradeRule();
        rule.setResource(DEGRADE_RESOURCE_NAME);
        rule.setGrade(RuleConstant.DEGRADE_GRADE_EXCEPTION_COUNT);
        //触发熔断异常数
        rule.setCount(2);
        //触发熔断的最小请求数
        rule.setMinRequestAmount(2);
        //统计时长:单位ms  1分钟
        rule.setStatIntervalMs(60*1000);
        //一分钟内:执行了两次 ,出现两次异常 就会触发熔断

        /**
         * 熔断持续时间,单位秒。一旦触发了熔断,再次请求接口则直接调用降级方法。
         * 10秒后,---半开状态,恢复接口调用。如果再次请求,则会熔断,不再根据熔断规则进入熔断,而是直接进入熔断
         */
        rule.setTimeWindow(10);


        rules.add(rule);
        DegradeRuleManager.loadRules(rules);
    }
}

流控规则一般设置在服务生产方,而降级规则一般设置在服务消费方

sentinel控制台部署

下载dashboard--https://github.com/alibaba/Sentinel/releases

运行jar包:java -jar sentinel-dashboard-1.8.0.jar。运行完毕进行访问,默认端口号8080。用户名和密码默认sentinel

客户端整合服务端

客户端需要引入Transport模块来与sentinel控制台进行通信

xml 复制代码
<!--sentinel整合dashbaord控制台-->
    <dependency>
      <groupId>com.alibaba.csp</groupId>
      <artifactId>sentinel-transport-simple-http</artifactId>
      <version>1.8.0</version>
    </dependency>
  • 配置启动
    客户端启动时需要加入JVM参数-Dcsp.sentinel.dashboard.server=192.168.1.15:8080,指定控制台地址和端口
相关推荐
零炻大礼包23 分钟前
【SQL server】数据库远程连接配置
数据库
zmgst32 分钟前
canal1.1.7使用canal-adapter进行mysql同步数据
java·数据库·mysql
随心............34 分钟前
python操作MySQL以及SQL综合案例
数据库·mysql
€☞扫地僧☜€35 分钟前
docker 拉取MySQL8.0镜像以及安装
运维·数据库·docker·容器
CopyDragon39 分钟前
设置域名跨越访问
数据库·sqlite
xjjeffery40 分钟前
MySQL 基础
数据库·mysql
写bug的小屁孩44 分钟前
前后端交互接口(三)
运维·服务器·数据库·windows·用户界面·qt6.3
恒辉信达1 小时前
hhdb数据库介绍(8-4)
服务器·数据库·mysql
齐 飞2 小时前
MongoDB笔记01-概念与安装
前端·数据库·笔记·后端·mongodb
云空2 小时前
《Python 与 SQLite:强大的数据库组合》
数据库·python·sqlite