Hystrix断路器
分布式系统面临的问题
扇出
多个微服务互相调用的时候,如果A调用B、C,而B、C又继续调用其他微服务,这就是扇出(像一把扇子一样慢慢打开。
服务雪崩
- 删除过程中,如果某一个环节的服务出现故障或连接超时,就会导致前面的服务占用越来越多的资源,进而引起系统崩溃,就是“雪崩效应”。
- 对于高流量的应用来说,单一的后端依赖会导致服务器所有的资源都在几秒钟内饱和。比失败更糟糕的是,这些应用程序还可能导致服务之间的延迟增加,备份队列,线程和其他系统资源紧张,导致整个系统发生更多的级联故障。这些都表示需要==对故障和延迟进行隔离和管理==,以便单个依赖关系的失败,不能取消整个应用程序或系统。
Hystrix介绍
- Hystrix是一个用于处理分布式系统延迟和容错的开源库。分布式系统中,依赖避免不了调用失败,比如超时,异常等。Hystrix能保证在出现问题的时候,不会导致整体服务失败,避免级联故障,以提高分布式系统的弹性。
- Hystrix类似一个“断路器”,当系统中异常发生时,断路器给调用返回一个符合预期的,可处理的FallBack,这样就可以避免长时间无响应或抛出异常,使故障不能再系统中蔓延,造成雪崩。
服务熔断
- 熔断机制的注解是@HystrixCommand
- 熔断机制是应对雪崩效应的一种==链路保护机制==,一般存在于服务端
- 当扇出链路的某个服务出现故障或响应超时,会进行==服务降级==,进而==熔断该节点的服务调用==,快速返回“错误”的相应信息。、
- Hystrix的熔断存在阈值,缺省是5秒内20次调用失败就会触发
熔断案例
- 构建一个新的provider module(如复制8001module)
- pom.xml加入hystrix依赖(一定要配合Eureka)
<dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-hystrix</artifactId> </dependency>
- application.xml中配置端口和Eureka信息(必配)和其他框架的配置信息(可选,如mybatis)
- 编写具体业务逻辑
- controller类中,在需要配置Fallback的方法上加入@@HystrixCommand(fallbackMethod = "XXX")注解,XXX为FallBack方法名本例中作为测试所以抛出了异常
@ResponseBody @GetMapping("/dept/{id}") @HystrixCommand(fallbackMethod = "nullDeptFallBack") public Dept findById(@PathVariable("id")Integer id) { Dept dept = deptService.findById(id); if (null == dept){ throw new RuntimeException("返回值为空!"); } return dept; }
- 根据需要配置FallBack的方法返回值编写代码
public Dept nullDeptFallBack(@PathVariable("id")Integer id) { System.out.println(111); return new Dept().setId(id).setDeptName("nullName").setDbSource("nullDB"); }
- 主启动类中加入@EnableCircuitBreaker注解
- 开启服务,测试
解耦与降级处理
降级
- 当系统整体资源快不够的时候,忍痛将部分服务暂时关闭,带渡过难关后,再重新开启。
- 降级处理时在==客户端==完成的,与服务端没有关系
- 理解:所谓降级,一般是从==整体负荷==考虑,当某个服务熔断之后,服务器将不再被调用,此时客户端可以自己准备一个本地的FallBack回调,返回一个缺省值。这样做虽然服务水平下降,但好歹可用,比直接挂掉好。
为什么要解耦
如果按照上面的熔断案例来做的话,Controller下的每个方法,都要给其编写一个FallBack方法,当方法慢慢变多,就会造成代码膨胀,一个是增加编写的工作量,另外一个也会增大维护的难度,代码的耦合度也会高,是十分不合理的,所以要将其解耦。
解耦思路
因为服务端的是通过实现接口访问服务端的,如果在父接口上实现了FallBack方法,通过这样一种方式去维护起来就能实现解耦,也顺便完成了降级的机制。
解耦&降级案例
- 在api模块中新建实现了FallbackFactory接口的类,其中泛型T就是我们需要维护其FallBack的接口方法,并实现其create方法,在create方法中返回实现了T的对象,使用匿名内部类实现T。==注意:这个类一定要加@Component注解!!这个类一定要加@Component注解!!这个类一定要加@Component注解!!==
import com.XXX.entity.Dept; import feign.hystrix.FallbackFactory; import org.springframework.stereotype.Component; import java.util.List; @Component public class DeptClientServiceFallBackFactory implements FallbackFactory<DeptClientService> { public DeptClientService create(Throwable throwable) { return new DeptClientService() { public boolean addDept(Dept dept) { return false; } public List<Dept> findAll() { return null; } public Dept findById(Integer id) { return new Dept().setId(id).setDeptName("服务器跪了,").setDbSource("迟点来吧"); } }; } }
- 修改步骤1中传入的泛型T接口,添加@FeignClient(fallbackFactory = T.class)注解
@FeignClient(value = "MICROSERVICECLOUD-DEPT",fallbackFactory = DeptClientServiceFallBackFactory.class) public interface DeptClientService { @PostMapping("/dept") public boolean addDept(Dept dept); @GetMapping("/dept") public List<Dept> findAll(); @GetMapping("/dept/{id}") public Dept findById(@PathVariable("id")Integer id); }
- 修改consumer feign模块的application.xml文件,开启hystrix(注:在IDEA中可能没有代码提示,开启的true也没有正常高亮,但好像不需要做额外操作也不影响结果)
feign: hystrix: enabled: true
- 开启服务并测试
HystrixDashboard服务监控
介绍:SpringCloud对Hystrix Dashboard进行了整合,可以对通过Hystrix发起的请求进行准实时统计,并以报表和图形的形式展示给用户(包括每秒执行多少次请求成功和失败等)。
配置案例
- 新建HystrixDashboard模块,pom.xml文件加入HystrixDashboard依赖,其他依赖包括Feign,Ribbon,Eureka(可参考80模块的依赖)
<dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-hystrix-dashboard</artifactId> </dependency>
- application.yml文件中配置端口(如9001)
- provider类中确认要加入actuator依赖(此为监控依赖)
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-actuator</artifactId> </dependency>
- 编写主启动类,上标@EnableHystrixDashboard标注
@SpringBootApplication @EnableHystrixDashboard public class DashBoard9001_APP { public static void main(String[] args) { SpringApplication.run(DashBoard9001_APP.class,args); } }
- 启动服务进行测试,访问地址:http://localhost:9001/hystrix,(根据配置端口号),==看到刺猬表示已经配置好了==
如何监控
- 在dashboard界面中,填入需要监控的服务地址和端口号加上\hystrix.stream和监测间隔即可进入监控。(如http://localhost:8001/hystrix.stream
监控分析
- 七色:进入监控界面后会有其中颜色的数字,其含义可以对应右上角相同颜色的单词表示的状态,其值代表该状态下触发的次数
- 一圈:圈的大小代表该服务的流量,圈越大流量越大
- 一线:代表监控间隔中,服务被访问的频率的折线图
- 通过观察这些就可以在大量的实例中找出故障实例和高压实例进行修复和维护。