SpringCloud 学习笔记系列03--Hystrix熔断器

Hystrix 简介

  • Hystrix 的中文含义是豪猪科动物,如下图所示, 因其背上长满了刺,而拥有自我保护能力.
  • Netflix的 Hystrix 是一个帮助解决分布式系统交互时超时处理和容错的类库, 它同样拥有保护系统的能力.
  • Hystrix是一个库,通过添加延迟容差和容错逻辑来帮助你控制这些分布式服务
    之间的交互,停止其间的级联故障以及提供回退选项,从而提供系统的整体弹性。
  • Hystrix执行的操作:
    • 1:对通过第三方客户端库访问(通常通过网络)的依赖关系提供保护并控制延迟和故障。
    • 2:隔离复杂分布式系统中的级联故障。
    • 3:快速发现故障,尽快恢复。
    • 4:回退,尽可能优雅地降级。
    • 5:启用近实时监控,警报和操作控制。
Hystrix熔断隔离流程

SpringCloud 学习笔记系列03--Hystrix熔断器

  • Hystrix隔离的核心思想就是按照接口进行线程池隔离.
  • Hystix熔断隔离流程说明:
    • 1.每次调用创建一个新的HystrixCommand,把依赖调用封装在run()方法中。
    • 2.执行execute()/queue做同步或异步调用。
    • 3.判断熔断器(circuit-breaker)是否打开,如果打开跳到步骤8,进行降级策略;如果关闭进入下一步骤。
    • 4.判断线程池/队列/信号量是否跑满,如果跑满进入降级步骤8,否则继续后续步骤。
    • 5.调用HystrixCommand的run()方法,运行依赖逻辑。如果依赖逻辑调用超时,进入步骤8.
    • 6.判断逻辑是否调用成功;如果成功,返回成功调用结果;如果调用出错,进入步骤8.
    • 7.计算熔断器状态,所有的运行状态(成功,失败,拒绝,超时)上报给熔断器,用于统计从而判断熔断器状态.
    • 8.getFallback()降级逻辑
      • a.没有实现getFallback的Command将直接抛出异常
      • b.fallback降级逻辑调用成功返回
      • c.降级逻辑调用失败抛出异常
    • 9.返回执行成功结果
  • 以下情况触发getFallback()逻辑:
    • 1.run()方法抛出非HystrixBadRequestException异常
    • 2.run()方法调用超时
    • 3.熔断器开启拦截调用
    • 4.线程池/队列/信号量是否饱满
两种资源隔离模式
  • 线程池隔离模式

    • 使用一个线程池来存储当前的请求,线程池对请求作处理,设置任务返回处理超时时间,堆积的请求堆积入线程池队列。
    • 这种方式需要为每个依赖的服务申请线程池,有一定的资源消耗,好处是可以应对突发流量(流量洪峰来临时,处理不完可将数据存储到线程池队里慢慢处理)
  • 信号量隔离模式

    • 使用一个原子计数器(或信号量)来记录当前有多少个线程在运行,请求来先判断计数器的数值,若超过设置的最大线程个数则丢弃改类型的新请求,若不超过则执行计数操作请求来计数器+1,请求返回计数器-1。
    • 这种方式是严格的控制线程且立即返回模式,无法应对突发流量(流量洪峰来临时,处理的线程超过数量,其他的请求会直接返回,不继续去请求依赖的服务)
  • 区别

    • 线程池隔离 信号量隔离
      线程 与调用线程非相同线程 与调用线程为相同线程(jetty线程)
      开销 排队、调度、上下文开销等 无线程切换,开销低
      异步 支持 不支持
      并发支持 支持(最大线程池大小) 支持(最大信号量上限)
  • 选用时机

    • Hystrix默认使用线程池隔离
    • 如果不涉及远程RPC调用(没用网络开销),比如访问内存缓存,则使用信号量来隔离,更为轻量,开销更小。
  • 线程池隔离:线程池核心配置

    • 参数 解释
      coreSize 核心线程数,maxSize
      keepAliveTime 空闲线程保存时间
      maxQueueSize 最大队列大小,如果-1则会使用交换队列
      queueSizeRejectionThreashold 当等待队列多大的时候,将会执行决策
      timeoutlnMiliseconds 执行线程的超时时间

Hystrix 配置

配置分类
  • Hystrix可以配置属性的一下类型:
    • Execution:控制HystrixCommand.run() 的如何执行
    • Fallback: 控制HystrixCommand.getFallback() 如何执行
    • Circuit Breaker: 控制断路器的行为
    • Metrics: 捕获和HystrixCommand 和 HystrixObservableCommand 执行信息相关的配置属性
    • Request Context:设置请求上下文的属性
    • Collapser Properties:设置请求合并的属性
    • Thread Pool Properties:设置线程池的属性
Hystrix参数的覆盖优先级
  • 优先级覆盖顺序:
    • 1、内置全局默认值:写死在代码里的值
    • 2、动态全局默认属性:通过属性文件配置全局的值
    • 3、内置实例默认值:写死在代码里的实例的值
    • 4、动态配置实例属性:通过属性文件配置特定实例的值
配置详解
  • @HystrixCommand注解
    • Hystrix支持两种方式定义HystrixCommand,一种是将类继承自HystrixCommand类,重写run方法。
    • 另一种是在方法头上写注解的方式。
    • 使用注解的方式代码会比较清晰,将Hystrix代码和业务代码隔离开
        // 设置所有实例的默认值
        hystrix.command.default.*=...
        // 设置实例HystrixCommandKey的此属性值
        hystrix.command.HystrixCommandKey.*=...
  • execution.isolation.strategy 隔离策略

    • 表示隔离策略,隔离策略有两种,一种为线程隔离一种为信号量隔离,
    •   @HystrixCommand(fallbackMethod = "error", commandProperties = {
                    //THREAD 线程隔离
                    //SEMAPHORE 信号量隔离
                    @HystrixProperty(name="execution.isolation.strategy", value = "THREAD")
            })
      
    • 默认是线程池隔离
  • execution.isolation.thread.timeoutInMilliseconds 请求线程总超时时间

    • 表示请求线程总超时时间,如果超过这个设置的时间hystrix就会调用fallback方法。
    •   @HystrixCommand(fallbackMethod = "error", commandProperties = {
                    @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds", value = "4000")
            })
      
    • value的参数为毫秒,默认值为1000ms。
  • execution.timeout.enabled 超时开关

    • 表示:当超时后是否触发fallback方法,默认为true。
  • execution.isolation.semaphore.maxConcurrentRequests 最大的并发请求量

    • 当隔离策略使用SEMAPHORE时,最大的并发请求量,如果请求超过这个最大值将拒绝后续的请求.
    • 默认值为10.
  • fallback.enabled 服务降级策略是否启用

    • 该属性用来设置服务降级策略是否启用,默认值 true ;
    • 如果设置为false,当请求失败或拒绝发生时,将不会调用 HystrixCommand.getFallback() 来执行服务降级逻辑
  • equestCache.enabled 是否开启请求缓存功能

    • 默认是:true
  • requestLog.enabled 表示是否开启日志,打印执行HystrixCommand的情况和事件

    • 默认是:true
  • hystrix.threadpool.default.coreSize 设置线程池的core的大小

    • 默认是:10
  • hystrix.threadpool.default.maximumSize 设置最大的线程池的大小

    • 只有设置allowMaximumSizeToDivergeFromCoreSize时,此值才起作用
    • 默认是:10
  • hystrix.threadpool.default.maxQueueSize 设置最大的BlockingQueue队列的值。

    • 如果设置-1,则使用SynchronousQueue队列,
    • 如果设置正数,则使用LinkedBlockingQueue队列
    • 默认是:-1
  • hystrix.threadpool.default.queueSizeRejectionThreshold

    • 因为maxQueueSize值不能被动态修改,所有通过设置此值可以实现动态修改等待队列长度。即等待的队列的数量大于queueSizeRejectionThreshold时(但是没有达到maxQueueSize值),则开始拒绝后续的请求进入队列。
    • 如果设置为-1,则属性不起作用
    • 默认是:5
  • hystrix.threadpool.default.keepAliveTimeMinutes 设置线程多久没有服务后,需要释放(maximumSize-coreSize )个线程

    • 默认是:1