SpringCloud Alibaba系列 Sentinel(三)
创始人
2024-01-18 12:17:06

高并发下的微服务容错方案?

  • 限流、熔断、降级

1:限流

在高并发系统中一定要用,高并发的所有请求进来,不是让每个请求都打到后台集群的,后台集群有它的消费能力,应该在它消费能力之内放行请求,这个就是限流

比如服务集群的处理能力是每秒1w,那么从网关处放过来的请求就是1w,超过1w的请求将直接丢弃,返回 “服务繁忙,稍后重试” 等字样。

2:熔断

一个服务常常会调用别的模块,可能是另外的一个远程服务、数据库,或者第三方 API 等。例如,支付的时候,可能需要远程调用银联提供的 API;查询某个商品的价格,可能需要进行数据库查询。然而,这个被依赖服务的稳定性是不能保证的。如果依赖的服务出现了不稳定的情况,请求的响应时间变长,那么调用服务的方法的响应时间也会变长,线程会产生堆积,最终可能耗尽业务自身的线程池,服务本身也变得不可用。

现代微服务架构都是分布式的,由非常多的服务组成。不同服务之间相互调用,组成复杂的调用链路。以上的问题在链路调用中会产生放大的效果。复杂链路上的某一环不稳定,就可能会层层级联,最终导致整个链路都不可用。因此我们需要对不稳定的弱依赖服务调用进行熔断降级,暂时切断不稳定调用,避免局部不稳定因素导致整体的雪崩。熔断降级作为保护自身的手段.

熔断就是在规定的时间内,下游服务还没有返回数据,上游服务在指定的时间内比如10秒内不调用下游服务,会在10秒后重新尝试调用下游服务,看下游服务是否正常响应了

3:降级

我们知道在一套完整的业务流程中是有主要的核心业务,和非核心业务的,比如电商系统中的商品、订单、支付是核心业务。推荐、优惠、附加业务(如小游戏)等是非核心业务。当服务流量很大的时候,可以降低非核心业务的可用性或者直接停掉。保证核心业务的可用。


分布式系统的流量防卫兵-Sentinel

官网:https://sentinelguard.io/zh-cn

github:https://github.com/alibaba/spring-cloud-alibaba/wiki/Sentinel

什么是 Sentinel ?

随着微服务的流行,服务和服务之间的稳定性变得越来越重要。Sentinel 是面向分布式、多语言异构化服务架构的流量治理组件,主要以流量为切入点,从流量路由、流量控制、流量整形、熔断降级、系统自适应过载保护、热点流量防护等多个维度来帮助开发者保障微服务的稳定性。

Sentinel 具有以下特征:

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

Sentinel 的主要概念

  • 资源

资源是 Sentinel 的关键概念。它可以是 Java 应用程序中的任何内容,例如,由应用程序提供的服务,或由应用程序调用的其它应用提供的服务,甚至可以是一段代码。在接下来的文档中,我们都会用资源来描述代码块。

只要通过 Sentinel API 定义的代码,就是资源,能够被 Sentinel 保护起来。大部分情况下,可以使用方法签名,URL,甚至服务名称作为资源名来标示资源。

  • 规则

围绕资源的实时状态设定的规则,可以包括流量控制规则、熔断降级规则以及系统保护规则。所有规则可以动态实时调整。


上手 Sentinel

  • 部署Sentinel控制台

  • 从 Github 上下载 Sentinel

https://github.com/alibaba/Sentinel

  • 启动 Sentinel 服务

注意:启动 Sentinel 控制台需要 JDK 版本为 1.8 及以上版本

注意:Sentinel 控制台目前仅支持单机部署。

使用如下命令启动控制台:

java -Dserver.port=8080 -Dcsp.sentinel.dashboard.server=localhost:8080 -Dproject.name=sentinel-dashboard -jar sentinel-dashboard.jar

其中 -Dserver.port=8080 用于指定 Sentinel 控制台端口为 8080

访问地址:http://ip:8080

默认账号密码:sentinel/sentinel


SpringCloud Alibaba 整合 Sentinel

maven版本管理如下

	17171717UTF-8UTF-82.7.42021.0.42021.0.4.0org.springframework.bootspring-boot-dependencies${spring.boot.version}pomimportorg.springframework.cloudspring-cloud-dependencies${spring.cloud.version}pomimportcom.alibaba.cloudspring-cloud-alibaba-dependencies${spring.cloud.alibaba.version}pomimport

子服务 pom 中添加依赖

com.alibaba.cloudspring-cloud-starter-alibaba-sentinel

application.yml 文件配置 sentinel

spring:cloud:sentinel:transport:port: 8719# sentinel 控制台地址dashboard: localhost:8080

这里的 spring.cloud.sentinel.transport.port 端口配置会在应用对应的机器上启动一个 Http Server,该 Server 会与 Sentinel 控制台做交互。比如 Sentinel 控制台添加了一个限流规则,会把规则数据 push 给这个 Http Server 接收,Http Server 再将规则注册到 Sentinel 中。这个端口不能被占用,多个微服务配置不同的port。若被占用,则端口自动+1

确保客户端有访问量,Sentinel 会在客户端首次调用的时候进行初始化,开始向控制台发送心跳包。微服务接口被请求后,就会在控制台显示出微服务


配置流控规则

注意:这里的配置规则是通过 调用 sentinel 提供的 HTTP API 接口来改变的,这也意味着这些规则仅在内存态生效,应用重启之后,该规则会丢失。关于持久化规则后面会讲到,请查看官网:在生产环境中使用 Sentinel · alibaba/Sentinel Wiki · GitHub

  • 测试一下流控效果

正常的请求拿到的数据如下

 当 一秒 时间里 请求次数超过 2 次,返回流控限制信息


流控控制面板介绍

流量控制 · alibaba/Sentinel Wiki · GitHub

资源名:默认是请求路径,可自定义,要保证唯一

针对来源:对哪个微服务进行限流,默认是不区分来源,全部限流,这个是针对 区分上游服务进行限流, 比如 视频服务 被 订单服务、用户服务调用,就可以针对订单服务来源进行限流,对用户服务来源不限流

阈值类型:

  • 流量控制
    • 原理是监控应用流量的 QPS 或并发线程数等指标,当达到指定的阈值时对流量进行控制,以避免被瞬时的流量高峰冲垮,从而保障应用的高可用性。
  • 两种规则
    1. 基于统计QPS的流量控制:当 QPS 超过某个阈值的时候,则采取措施进行流量控制
    2. 基于统计并发线程数的流量控制:并发数控制用于保护业务线程池不被慢调用耗尽。Sentinel 并发控制不负责创建和管理线程池,而是简单统计当前请求上下文的线程数目(正在执行的调用数目)如果超出阈值,新的请求会被立即拒绝,效果类似于信号量隔离。

流控效果介绍

快速失败

默认的流量控制方式,当QPS超过任意规则的阈值后,新的请求就会被立即拒绝

Warm Up

即预热/冷启动方式。当系统长期处于低水位的情况下,当流量突然增加时,直接把系统拉升到高水位可能瞬间把系统压垮。通过"冷启动",让通过的流量缓慢增加,在一定时间内逐渐增加到阈值上限,给冷系统一个预热的时间,避免冷系统被压垮。

排队等待

严格控制请求通过的间隔时间,也即是让请求以均匀的速度通过,对应的是漏桶算法,主要用于处理间隔性突发的流量,如消息队列,想象一下这样的场景,在某一秒有大量的请求到来,而接下来的几秒则处于空闲状态,我们希望系统能够在接下来的空闲期间逐渐处理这些请求,而不是在第一秒直接拒绝多余的请求。

  • 匀速排队等待策略是 Leaky Bucket 算法结合虚拟队列等待机制实现的。
  • 注意:匀速排队模式暂时不支持 QPS > 1000 的场景,不能让用户无限的排对,不然等到啥时候去了?

熔断降级介绍

慢调用比例

选择以慢调用比例作为阈值,需要设置允许的慢调用 RT(即最大的响应时间),请求的响应时间大于该值则统计为慢调用。当单位统计时长(statIntervalMs)内请求数目大于设置的最小请求数目,并且慢调用的比例大于阈值,则接下来的熔断时长内请求会自动被熔断。经过熔断时长后熔断器会进入探测恢复状态(HALF-OPEN 状态),若接下来的一个请求响应时间小于设置的慢调用 RT 则结束熔断,若大于设置的慢调用 RT 则会再次被熔断。

示例:

同下面的异常比例、异常数类似,就不贴示例了

异常比例

当单位统计时长(statIntervalMs)内请求数目大于设置的最小请求数目,并且异常的比例大于阈值,则接下来的熔断时长内请求会自动被熔断。经过熔断时长后熔断器会进入探测恢复状态(HALF-OPEN 状态),若接下来的一个请求成功完成(没有错误)则结束熔断,否则会再次被熔断。异常比率的阈值范围是 [0.0, 1.0],代表 0% - 100%。 

异常数

当单位统计时长内的异常数目超过阈值之后会自动进行熔断。经过熔断时长后熔断器会进入探测恢复状态(HALF-OPEN 状态),若接下来的一个请求成功完成(没有错误)则结束熔断,否则会再次被熔断。


权限介绍

很多时候,我们需要根据调用来源来判断该次请求是否允许放行,这时候可以使用 Sentinel 的来源访问控制(黑白名单控制)的功能。来源访问控制根据资源的请求来源(origin)限制资源是否通过,若配置白名单则只有请求来源位于白名单内时才可通过;若配置黑名单则请求来源位于黑名单时不通过,其余的请求通过。


自定义流控熔断返回的JSON信息

import com.alibaba.csp.sentinel.adapter.spring.webmvc.callback.BlockExceptionHandler;
import com.alibaba.csp.sentinel.slots.block.BlockException;
import com.alibaba.csp.sentinel.slots.block.authority.AuthorityException;
import com.alibaba.csp.sentinel.slots.block.degrade.DegradeException;
import com.alibaba.csp.sentinel.slots.block.flow.FlowException;
import com.alibaba.csp.sentinel.slots.block.flow.param.ParamFlowException;
import com.alibaba.csp.sentinel.slots.system.SystemBlockException;
import com.alibaba.fastjson.JSON;
import org.springframework.stereotype.Component;import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.HashMap;
import java.util.Map;@Component
public class CustomUrlBlockHandler implements BlockExceptionHandler {@Overridepublic void handle(HttpServletRequest request, HttpServletResponse response, BlockException e) throws Exception {Map backMap = new HashMap<>(2);if (e instanceof FlowException) {backMap.put("code", -1);backMap.put("msg", "限流-异常啦");} else if (e instanceof DegradeException) {backMap.put("code", -2);backMap.put("msg", "降级-异常啦");} else if (e instanceof ParamFlowException) {backMap.put("code", -3);backMap.put("msg", "热点-异常啦");} else if (e instanceof SystemBlockException) {backMap.put("code", -4);backMap.put("msg", "系统规则-异常啦");} else if (e instanceof AuthorityException) {backMap.put("code", -5);backMap.put("msg", "认证-异常啦");}response.setHeader("Access-Control-Allow-Origin", "*");response.setHeader("Cache-Control", "no-cache");response.setStatus(200);response.setCharacterEncoding("UTF-8");response.setContentType("application/json");response.getWriter().println(JSON.toJSONString(backMap));response.getWriter().flush();}
}


Feign 整合 Sentinel

子服务 pom 中添加依赖

org.springframework.cloudspring-cloud-starter-openfeign

com.alibaba.cloudspring-cloud-starter-alibaba-sentinel

application.yml 文件配置 打开Sentinel对Feign的支持

feign:sentinel:enabled: true

相关内容

热门资讯

埃菲尔铁塔在哪 中国仿建埃菲尔... 2019年4月26日,广西南宁市,街头惊现一座巨型山寨版埃菲尔铁塔,高约20米,白色塔身,造型逼真,...
苗族的传统节日 贵州苗族节日有... 【岜沙苗族芦笙节】岜沙,苗语叫“分送”,距从江县城7.5公里,是世界上最崇拜树木并以树为神的枪手部落...
苁蓉的食用方法 鲜苁蓉的吃法有... 肉苁蓉号称“温而不热,补而不峻,暖而不燥,滑而不泄,故有从容之名。”历来也是传统药食同源的滋补佳品。...
北京的名胜古迹 北京最著名的景... 北京从元代开始,逐渐走上帝国首都的道路,先是成为大辽朝五大首都之一的南京城,随着金灭辽,金代从海陵王...
应用未安装解决办法 平板应用未... ---IT小技术,每天Get一个小技能!一、前言描述苹果IPad2居然不能安装怎么办?与此IPad不...
脚上的穴位图 脚面经络图对应的... 人体穴位作用图解大全更清晰直观的标注了各个人体穴位的作用,包括头部穴位图、胸部穴位图、背部穴位图、胳...
长白山自助游攻略 吉林长白山游... 昨天介绍了西坡的景点详细请看链接:一个人的旅行,据说能看到长白山天池全凭运气,您的运气如何?今日介绍...
猫咪吃了塑料袋怎么办 猫咪误食... 你知道吗?塑料袋放久了会长猫哦!要说猫咪对塑料袋的喜爱程度完完全全可以媲美纸箱家里只要一有塑料袋的响...
世界上最漂亮的人 世界上最漂亮... 此前在某网上,选出了全球265万颜值姣好的女性。从这些数量庞大的女性群体中,人们投票选出了心目中最美...
埃菲尔铁塔在哪 中国仿建埃菲尔... 2019年4月26日,广西南宁市,街头惊现一座巨型山寨版埃菲尔铁塔,高约20米,白色塔身,造型逼真,...
阳澄湖在哪里哪个省的 阳澄湖是... 点击题目下方苏州生活指南有用 有趣 有态度近期的阳澄湖度很高,3月24日,央视二套《第一时间》直播连...
苗族的传统节日 贵州苗族节日有... 【岜沙苗族芦笙节】岜沙,苗语叫“分送”,距从江县城7.5公里,是世界上最崇拜树木并以树为神的枪手部落...
北京的名胜古迹 北京最著名的景... 北京从元代开始,逐渐走上帝国首都的道路,先是成为大辽朝五大首都之一的南京城,随着金灭辽,金代从海陵王...