Hystrix 服务熔断降级

引言

Hystrix 属于 Spring Cloud Netflix 中的套件之一,Spring Cloud Netflix 其中还包括Eureka,Feign,Ribbon,Zuul,Bus。本文仅简单讲一下Hystrix这个熔断降级框架。
为什么不讲sentinel呢,因为sentinel的官方文档全中文,并且使用也很方便,只要是个正常人,我觉得不需要单写一篇文章来讲,所以我只写过alibabaseata的文章。

基本概念

  • 区分上下游服务
    下游服务请求方上游服务接受请求,并返回响应的一方。(很多人把上下游搞混,在王夕宁Istio那本书中有明确定义,且Nginx之类中upstream也代表的是接收请求的一方。)
  • 什么是服务熔断
    服务熔断机制是为了保证当服务产生调用链后,避免上游服务出现问题导致下游服务跟着受罪,致使整个应用中的服务发生雪崩
  • 什么是服务降级?
    触发熔断机制后,服务就会被降级,说人话就是断路器打开时,当下游服务请求上游服务,直接返回失败内容,不需要上游服务真的去工作。
    举个栗子:应用中有很多服务,用户服务,订单服务,ID生成服务等等,当订单服务触发熔断机制导致服务降级后,应用中其他功能都不会受到影响,仅是订单服务是不可用状态,而不会导致整个应用所有功能都无法使用。
  • 为什么需要服务熔断
    当上游服务工作量达到瓶颈,CPU已经撑不住了,之后来的请求已经无法处理,如果这时不熔断就会导致下游服务的请求得不到回应,一直等待上游服务回应,下游服务的下游服务同样会等待,整个调用链都在等待,这样会把本来正常的服务也阻塞住,请求增多后就会导致整个应用的服务都成了不可用的状态。

注解开启断路器

@EnableHystrix注解的作用和@EnableCircuitBreaker注解的作用一样,@EnableHystrix注解对EnableCircuitBreaker注解进行了封装。所以使用Hystrix时用哪个注解都可以.

策略配置

首先需要区分的是,在Ribbon中的请求超时Hystrix中的超时是不同的,如果Hystrix中配置timeoutInMilliseconds<Ribbon中的ReadTimeout,这可能并不是你想要的结果,因为一旦触发Hystrix中的超时就会立即产生服务熔断,不会达到重试的目的。timeoutInMilliseconds的配置应 > Ribbon (1 + MaxAutoRetries + MaxAutoRetriesNextServer) * ReadTimeout

@DefaultProperties和@HystrixCommand

@DefaultProperties注解是用在Controller上的默认配置,在控制器方法上没有使用@HystrixCommand时,就会使用@DefaultProperties的配置。

简单的超时配置

@DefaultProperties(defaultFallback = "defaultFallBack",commandProperties = {@HystrixProperty(name="execution.isolation.thread.timeoutInMilliseconds", value="1000")}) //Hystrix 定义全局 设置
public class HomeController {
    //@Autowired
    //private RestTemplate restTemplate;


    @Qualifier("pay-server")
    @Autowired
    private IPayService payService;

    @Autowired
    private ConsulDiscoveryClient discoveryClient;

    @GetMapping("getOrder")
    @HystrixCommand(commandProperties = {@HystrixProperty(name="execution.isolation.thread.timeoutInMilliseconds", value="5000")})
    public String getOrder() throws ExecutionException, InterruptedException {
        return payService.getOrder();
    }
    
	private String defaultFallBack() {
        return "默认降级提示:请稍后重试~";
    }
}

默认情况下,控制器内其他方法超时都是1秒,仅getOrder的配置会被替换,变成5秒。

其他配置

配置中我们可以看见commandProperties配置了超时,commandProperties接受的是@HystrixProperty的列表,所以其中还有其他的配置可以设置。
我们可以在com.netflix.hystrix.HystrixCommandProperties中找到所有的配置项。
其中有隔离策略,断路器打开后的等待时间,错误阈值等等。

隔离策略

比如 execution.isolation.strategy 直译就是执行隔离策略,默认的情况下是ExecutionIsolationStrategy.THREAD,意思就是线程隔离。
隔离策略中还有一个策略是ExecutionIsolationStrategy.SEMAPHORE,意思就是信号量,你可以理解为QPS。

默认情况下是根据threadPoolKeygroupKey进行区分。
如果没有规定,groupKey的默认值是使用@HystrixCommand标注的方法所在的类名
这就相当于对服务的接口进行限流,当超过阈值后就会触发熔断

如果想更改为信号量模式可以使用:
@HystrixProperty(name="execution.isolation.strategy", value="SEMAPHORE")
更改信号量模式下固定时间内(默认是1秒)最大请求数限制:
@HystrixProperty(name="execution.isolation.semaphore.maxConcurrentRequests", value="10")

threadPoolProperties

@DefaultProperties@HystrixCommand中 还有threadPoolProperties的配置。
在默认使用线程池隔离时,你可以通过threadPoolProperties 配置线程池大小,如果需要可以也可以修改线程池队列大小。

@DefaultProperties(defaultFallback = "defaultFallBack",
        threadPoolProperties = { @HystrixProperty(name="coreSize",value = "10"),
                //@HystrixProperty(name="maxQueueSize",value = "5"), //如果改了 就会从无界队列变为有界队列
                //@HystrixProperty(name="queueSizeRejectionThreshold",value = "5")//队列大小的拒绝阈值 这个值最好设置成和队列大小相同
        },
        commandProperties = { @HystrixProperty(name="execution.isolation.thread.timeoutInMilliseconds", value="5000")
        }
 }

断路器状态

Hystrix断路器有3种状态:

  • 打开
    断路器打开状态下,任何请求过来直接进行降级,返回fallback内容
  • 半开
    当断路器在打开的状态下,等待固定时间后,转为半开状态,尝试处理部分请求,如果都正常才会关闭断路器。
  • 关闭
    断路器关闭状态下,正常处理所有请求。

断路器时间配置

上面讲了如何通过@HystrixProperty自己配置一些额外设置,现在就可以使用它对circuitBreaker.sleepWindowInMilliseconds进行配置,这就是在断路器处于打开状态下,需要等待多久会进入半开状态,默认值是5秒。

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

没事干写博客玩

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值