天天看点

Sentinel-基础Sentinel

服务保护的基本概念

服务限流

服务限流目的是为了更好的保护我们的服务,在高并发的情况下,如果客户端请求的数量达到一定极限(后台可以配置阈值),请求的数量超出了设置的阈值,开启自我的保护,直接调用我们的服务降级的方法,不会执行业务逻辑操作,直接走本地 falback 的方法,返回一个友好的提示。

服务降级

在高并发的情况下, 防止用户一直等待,采用限流/熔断方法,使用服务降级的方式返回一个友好的提示给客户端,不会执行业务逻辑请求,直接走本地的falback的方法。

提示语:当前排队人数过多,稍后重试~

服务雪崩

默认的情况下,Tomcat或者是Jetty服务器只有一个线程池去处理客户端的请求,这样的话就是在高并发的情况下,如果客户端所有的请求都堆积到同一个服务接口上, 那么就会产生tomcat服务器所有的线程都在处理该接口,可能会导致其他的接口无法访问。

假设我们的tomcat线程最大的线程数量是为20,这时候客户端如果同时发送100个请求会导致有80个请求暂时无法访问,就会转圈。

服务雪崩的解决方案:服务隔离机制:线程池隔离或者信号量隔离机制

  1. 线程池隔离机制:每个服务接口都有自己独立的线程池,互不影响,缺点就是占用cpu资源非常大。
  2. 信号量隔离机制:最多只有一定的阈值线程数处理我们的请求,超过该阈值会拒绝请求。

Sentinel

前哨以流量为切入点,从流量控制,熔断降级,系统负载保护等多个维度保护服务的稳定性。

前哨具有以下特征:

  1. 丰富的应用场景:前哨兵承接了阿里巴巴近10年的双十一大促流的核心场景,例如秒杀(即突然流量控制在系统容量可以承受的范围),消息削峰填谷,传递流量控制,实时熔断下游不可用应用等。
  2. 完备的实时监控:Sentinel同时提供实时的监控功能。您可以在控制台中看到接收应用的单台机器秒级数据,甚至500台以下规模的整合的汇总运行情况。
  3. 广泛的开源生态:Sentinel提供开箱即用的与其他开源框架/库的集成模块,例如与Spring Cloud,Dubbo,gRPC的整合。您只需要另外的依赖并进行简单的配置即可快速地接入Sentinel。
  4. 完善的SPI扩展点:Sentinel提供简单易用,完善的SPI扩展接口。您可以通过实现扩展接口来快速地定制逻辑。例如定制规则管理,适应动态数据源等。

Sentinel中文文档介绍:https://github.com/alibaba/Sentinel/wiki/%E4%BB%8B%E7%BB%8D

Sentinel 与hytrix区别

Sentinel-基础Sentinel

重点区别:熔断降级策略、限流、流量整形、系统保护支持、控制台、Sentinel 支持的框架多。

限流配置

官方文档:https://github.com/alibaba/Sentinel/wiki/%E5%A6%82%E4%BD%95%E4%BD%BF%E7%94%A8

手动使用代码配置 纯代码或者注解的形式配置

这种方式不需要 sentinel 仪表盘项目。

maven依赖的引入

<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-alibaba-sentinel</artifactId>
    <version>0.2.2.RELEASE</version>

</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
           

第一种方式: java代码

private static final String GETORDER_KEY = "getOrder";

@RequestMapping("/initFlowQpsRule")
public String initFlowQpsRule() {
    List<FlowRule> rules = new ArrayList<FlowRule>();
    FlowRule rule1 = new FlowRule();
    rule1.setResource(GETORDER_KEY);
    // QPS控制在2以内
    rule1.setCount(1);
    // QPS限流
    rule1.setGrade(RuleConstant.FLOW_GRADE_QPS);
    rule1.setLimitApp("default");
    rules.add(rule1);
    FlowRuleManager.loadRules(rules);
    return "....限流配置初始化成功..";
}


@RequestMapping("/getOrder")
public String getOrders() {
    Entry entry = null;
    try {
        entry = SphU.entry(GETORDER_KEY);
        // 执行我们服务需要保护的业务逻辑
        return "getOrder接口";
    } catch (Exception e) {
        e.printStackTrace();
        return "该服务接口已经达到上线!";
    } finally {
        // SphU.entry(xxx) 需要与 entry.exit() 成对出现,否则会导致调用链记录异常
        if (entry != null) {
            entry.exit();
        }
    }

}
           

第二种方式: 手动放入到项目启动自动加载

@Component
@Slf4j
public class SentinelApplicationRunner implements ApplicationRunner {
    private static final String GETORDER_KEY = "getOrder";

    @Override
    public void run(ApplicationArguments args) throws Exception {
        List<FlowRule> rules = new ArrayList<FlowRule>();
        FlowRule rule1 = new FlowRule();
        rule1.setResource(GETORDER_KEY);
        // QPS控制在2以内
        rule1.setCount(1);
        // QPS限流
        rule1.setGrade(RuleConstant.FLOW_GRADE_QPS);
        rule1.setLimitApp("default");
        rules.add(rule1);
        FlowRuleManager.loadRules(rules);
        log.info(">>>限流服务接口配置加载成功>>>");
    }
}
           

第三种方式: 注解形式配置管理Api限流

@SentinelResource value参数:流量规则资源名称、

blockHandler 限流/熔断出现异常执行的方法

Fallback 服务的降级执行的方法

注解属性:

  1. value:资源名称,必需项,由于须要经过resource name找到对应的规则,这个是必须配置的。code
  2. entryType:entry 类型,可选项,

    有IN和OUT两个选项,默认为 EntryType.OUT。xml

  3. blockHandler:blockHandler 对应处理 BlockException 的函数名称,可选项。blockHandler 函数访问范围须要是 public,返回类型须要与原方法相匹配,参数类型须要和原方法相匹配而且最后加一个额外的参数,类型为 BlockException。对象
  4. blockHandlerClass:blockHandler 函数默认须要和原方法在同一个类中,若是但愿使用其余类的函数,则须要指定 blockHandlerClass 为对应的类的 Class 对象,注意对应的函数必需为 static 函数,不然没法解析。
  5. fallback:fallback 函数名称,可选项,用于在抛出异常的时候提供 fallback 处理逻辑。fallback 函数能够针对全部类型的异常(除了 exceptionsToIgnore 里面排除掉的异常类型)进行处理。资源
  6. fallbackClass:fallbackClass的应用和blockHandlerClass相似,fallback 函数默认须要和原方法在同一个类中。

    若但愿使用其余类的函数,则能够指定 fallbackClass 为对应的类的 Class 对象,注意对应的函数必需为 static 函数,不然没法解析。

  7. defaultFallback(since 1.6.0):若是没有配置defaultFallback方法,默认都会走到这里来。默认的 fallback 函数名称,可选项,一般用于通用的 fallback 逻辑。默认 fallback 函数能够针对全部类型的异常(除了 exceptionsToIgnore 里面排除掉的异常类型)进行处理。若同时配置了 fallback 和 defaultFallback,则只有 fallback 会生效。
  8. exceptionsToIgnore(since 1.6.0):用于指定哪些异常被排除掉,不会计入异常统计中,也不会进入 fallback 逻辑中,而是会原样抛出。
@SentinelResource(value = GETORDER_KEY, blockHandler = "getOrderQpsException")
@RequestMapping("/getOrderAnnotation")
public String getOrderAnnotation() {
    return "getOrder接口";
}

/**
 * 被限流后返回的提示
 *
 * @param e
 * @return
 */
public String getOrderQpsException(BlockException e) {
    e.printStackTrace();
    return "该接口已经被限流啦!";
}
           

Sentinel 控制台形式配置

下载对应Sentinel-Dashboard 下载地址。

运行执行下面命令

java -Dserver.port=8718 -Dcsp.sentinel.dashboard.server=localhost:8718 -Dproject.name=sentinel-dashboard -Dcsp.sentinel.api.port=8719 -jar  jar包名称
           

安装好之后请求路径:http://localhost:8718/

登录页面

Sentinel-基础Sentinel

控制台页面

Sentinel-基础Sentinel

springboot项目整合 sentinel控制台

在上面的基础上增加 yml 配置

spring:
  application:
    name: kaico-sentinel-demo
  cloud:
    #sentinel仪表盘连接信息
    sentinel:
      transport:
        dashboard: 127.0.0.1:8718
      eager: true
           

启动项目后,可以在控制台看见服务名称,这是限流规则可以实时修改并且生效。

Sentinel-基础Sentinel

接口上没有加注解的话,资源名称默认为@RequestMapping注解的value的值(注意:是全部value的值。包括

/

),默认sentinel 会有自己的限流返回信息。

Sentinel-基础Sentinel

在控制台添加限流规则

Sentinel-基础Sentinel

资源名称:如果被限流的方法上有注解

@SentinelResource

,则使用注解中指定的名称,没有的话使用使用

@RequestMapping、@GetMapping等注解

的value的值

QPS:表示一秒钟处理多少个请求

线程数:就是信号量隔离,同一时刻最多只有多少个线程处理请求。