SpringCloud-容错处理Hystrix熔断器(五)

前言:微服务架构应用的特点就是多服务,而服务层之间通过网络进行通信,从而支撑起整个应用系统,所以,各个微服务之间不可避免的存在耦合依赖关系。但任何的服务应用实例都不可能永远的健康或网络不可能永远的都相安无事,所以一旦某个服务或局部业务发生了故障,会导致系统的不可用,我们知道当故障累积到一定程度就会造成系统层面的灾害,也就是级联故障,也叫雪崩效应,所以微服务需要在故障累计到上限之前阻止或疏通这些故障以保证系统的稳固安全,在市面上已经有很多这样的框架来解决这样的问题,如Twitter的Finagle、Netflix的Hystrix和Google的Stubby等,下面就简单介绍下Hystrix和Hystrix在SpringCloud中的应用。

一、Hystrix简介

  Hystrix(https://github.com/Netflix/Hystrix)是由Netflix开源的一个延迟和容错库,用于隔离访问远程系统、服务或者第三方库,防止级联失败,从而提升系统的可用性、容错性与局部应用的弹性,是一个实现了超市机制和断路器模式的工具类库。

二、Hystrix如何解决依赖隔离

  1、包裹请求:使用HystrixCommand包裹对依赖的调用逻辑,每个命令在独立的线程中执行,使用了设计模式中的“命令模式”;   2、跳闸机制:当某服务的错误率超过一定阈值时,Hystrix可以自动或者手动跳闸,停止请求该服务一段时间;   3、资源隔离:Hystrix为每个依赖都维护了一个小型的线程池(或者信号量)。如果该线程已满,则发向该依赖的请求就会被立即拒绝,而不是排队等候,从而加速失败判定;   4、监控:Hystrix可以近乎实时地监控运行指标和配置的变化,例如成功、失败、超时、以及被拒绝的请求等;   5、回退机制:当请求失败、超时、被拒绝,或当断路器打开时,执行回退逻辑,回退逻辑由开发人员自行提供,如返回一个缺省值;   6、自我修复:断路器打开一段时间后,会自动进入“半开”状态,此时断路器可允许一个请求访问依赖的服务,若请求成功,则断路器关闭,否则断路器转为“打开”状态;

三、Hystrix在SpringCloud中的简单应用

1、简单整合Hystrix(在这部分会用到Ribbon测试的相关项目)

  ①、创建基于Eureka和Ribbon的服务端 eureka-ribbon-server和两个客户端生产者 eureka-ribbon-client2、消费者:复制项目eureka-ribbon-client,将AritfactId修改为eureka-hystrix-client;

  ②、在消费者中添加依赖:

    <dependency>
      <groupId>org.springframework.cloud</groupId>
      <artifactId>spring-cloud-starter-hystrix</artifactId>
    </dependency>

  ③、在启动类ClientApplication上添加@EnableHystrix或@EnableCircuitBreaker;

  ④、修改HystrixController,在其中添加getUser方法,并添加熔断回调方法注解及回调方法:

    @HystrixCommand(fallbackMethod = "getDefaultUser")
    @RequestMapping("/getUser")
    public String getUser() {
        return restTemplate.getForObject("http://client-87/getUser", String.class);
    }

    private String getDefaultUser() {
        System.out.println("熔断,默认回调函数");
        return "{\"username\":\"admin\",\"age\":\"-1\"}";
    }

  ⑤、分别启动eureka-ribbon-server、eureka-ribbon-client2、eureka-hystrix-client,调用localhost:8765/getUser,如图:

  ⑥、关掉eureka-ribbon-client2后,再次调用,发现熔断器调用了回调函数,如图:

  关于Hystrix的配置属性,可以自行测试了解:https://github.com/Netflix/Hystrix/tree/master/hystrix-contrib/hystrix-javanica#configuration

  而我们如何知道hystrix是否开启,可以通过SpringBoot Actuator组件查看,注意:出发回调并不是hystrix打开,他的状态还处在关闭,若失败率达到阈值(默认为5秒内20次失败)后才会打开;

2、基于Feign使用Hystrix

  通常情况下的Hystrix是通过注解@HystrixCommand的fallbackMethod属性实现回调的,而在Feign中,由于Feign是用借口实现的声明式Rest,所以Hystrix的通用方法在这里就不适用于Feign了,实际上在Feign与SpringCloud的依赖库中已经默认的将Hystrix加入其中了,如图:

  那么,该怎么实现呢?

  1. 将上面通用Hystrix的项目中的消费者模块修改为,由于feign中已经集成了hystrix类库,所以就不需要重复导入了:

  pom.xml:

    <dependency>
      <groupId>org.springframework.cloud</groupId>
      <artifactId>spring-cloud-starter-feign</artifactId>
    </dependency>

  application.properties属性配置文件:

server.port=8762
spring.application.name=client-8762
#默认feign的hystrix为关闭状态
feign.hystrix.enabled=true
eureka.client.service-url.defaultZone=http://localhost:8761/eureka/

  启动类添加@EnableFeignClients,控制层通过注入feign的接口去完成声明式调用:

  feign的接口:

package com.cn.feign;

import org.springframework.cloud.netflix.feign.FeignClient;
import org.springframework.web.bind.annotation.RequestMapping;
//接口类上加入的注解中添加属性fallback,指定回调类
@FeignClient(name = "CLIENT-87",fallback = FeignClientFallback.class)
public interface UserFeign {

    @RequestMapping("/getUser")
    public String getUser();

}

  创建回调类:

package com.cn.feign;

import org.springframework.stereotype.Component;

/**
 * @Description: 回调实现类
 * @Param:
 * @return:  
 * @Author:  
 * @Date: 2018/6/19 
 */ 
@Component
class FeignClientFallback implements UserFeign {

    @Override
    public String getUser() {
        System.out.println("熔断,默认回调函数");
        return "{\"username\":\"admin\",\"age\":\"-1\"}";
    }
}

  2.测试结果如下:

  在未关闭生产者服务实例时:

  关闭实例后:

代码示例:https://gitee.com/lfalex/springcloud-exampleeureka-hystrix-clienteureka-feign-hystrix-clienteureka-ribbon-client2eureka-ribbon-server

参考书籍:《SpringCloud与Docker微服务架构实战》周力著

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏Java成长之路

idea创建maven项目时一直显示“Loading archetype list ”

1856
来自专栏编程软文

SpringCloud微服务框架搭建

3839
来自专栏JackieZheng

可视化工具gephi源码探秘(一)

  今天在老大和小梁的鼓舞和忽悠下(^_^),我决定还是把之前下载好的gephi源码好好利用起来,不在朝三暮四的想d3js或是什么vizster,用心去选择一个...

2395
来自专栏一英里广度一英寸深度的学习

Flume 日志收集系统 Spooldir-Source HDFS-sink

消息 Record,Source封装Event(事件)成为Record对象,并保存到Channel中,Sink拉取Record并保存到目标系统中。

4984
来自专栏JAVA技术zhai

以Spring Cloud为基础的微服务架构提出与落地

微服务架构模式的核心在于如何识别服务的边界,设计出合理的微服务。但如果要将微服务架构运用到生产项目上,并且能够发挥该架构模式的重要作用,则需要微服务框架的支持。...

4137
来自专栏漏斗社区

NSA工具包实战--32位XP系统(MS17-010)

近期因为工控安全大赛的原因,遇到了32系统存在17-010用matesploit无法利用的缘故。目前斗哥的metasploit v4.17.2-dev只支持wi...

3141
来自专栏Netkiller

跟我学 systemd

跟我学 systemd 摘要 我的系列文档 Netkiller Architect 手札Netkiller Developer 手札Netkiller PHP ...

38112
来自专栏Rainbond开源「容器云平台」

【Rainbond最佳实践】Spring Boot框架配置MySQL

1082
来自专栏CSDN技术头条

快速实战 Spring Boot

解释一下:Spring Boot 可以构建一切。Spring Boot 设计之初就是为了最少的配置,最快的速度来启动和运行 Spring 项目。Spring B...

1445
来自专栏Java 源码分析

SpringCloud:Eureka服务注册与发现

Eureka 其实就是一个 服务注册与发现的中心,也就是相当于我们前面做的一些生产者的服务需要注册到我们的注册中心,那么我们的消费者就不用把代码写死,而是可以去...

1883

扫码关注云+社区

领取腾讯云代金券