Hystrix 配合 Feign 使用

Hystrix 配合 Feign 使用

注:该授权部分是自己研究出来的,可能存在争议

Hystrix 简称熔断器、断路器,当接口发生访问错误或者并发量太高导致接口出现故障时,Hystrix 可以根据既定规则对该接口之后的请求进行引导(执行回退函数等),防止系统过载或形成雪崩效应。

Feign 可以使用其进行声明式的 REST 接口调用,简化微服务调用方式,并且 Feign 支持微服务接口授权调用。

经过研究发现,Hystrix 和 Feign 官方又提供无授权验证(验证是否有权限调用接口)接口调用版本的整合,但是无需授权才能调用的接口的整合。

一、使用 Hystrix 和 Feign 整合调用微服务无需授权接口

1、向项目中添加 Hystrix

<!-- 声明书 Rest 调用 Feign -->
<dependency>
     <groupId>org.springframework.cloud</groupId>
     <artifactId>spring-cloud-starter-openfeign</artifactId>
</dependency>
<!-- end -->
<!-- 熔断器 -->
<!-- https://mvnrepository.com/artifact/org.springframework.cloud/spring-cloud-starter-netflix-hystrix -->
<dependency>
      <groupId>org.springframework.cloud</groupId>
      <artifactId>spring-cloud-starter-netflix-hystrix</artifactId>
      <version>2.2.4.RELEASE</version>
</dependency>
<!-- end -->

具体版本号可以去 Maven Repository: org.springframework.cloud » spring-cloud-starter-netflix-hystrix (mvnrepository.com) 这里查找。

2、向启动器添加 @EnableCircuitBreaker注解

3、使用 @HystrixCommand注解为接口指定回退方法和一些参数。

常用的参数有:

4、Feign 使用 Hystrix,在 @FeignClient 注解中有 fallback 属性,可以使用该属性为 FeignClient 接口指定回退类,示例如下:

@FeignClient(name = "user-info-server",fallback = UserInfoServerClientFallback.class)
public interface UserInfoServerClient
{
    /**
     * user-info-server 使用情况
     * @return
     */
    @RequestMapping(value = "/sys/usage",method = RequestMethod.GET)
    public Object usage();
}

@Component
public class UserInfoServerClientFallback implements UserInfoServerClient
{
    @Override
    public Object usage ()
    {
        return new HashMap<String,String>(0);
    }
}

5、当我们需要记录回退(也就是为啥子调用出错)的原因的时候,只需使用 @FeignClient 中的 fallbackFactory 属性指定回退工厂,该回退工厂需实现 FallbackFactory 接口。示例如下:

@FeignClient(name = "user-info-server",fallbackFactory = "UserInfoServerClientFallbackFactory")
public interface UserInfoServerClient
{
    /**
     * user-info-server 使用情况
     * @return
     */
    @RequestMapping(value = "/sys/usage",method = RequestMethod.GET)
    public Object usage();
}

@Component
public class UserInfoServerClientFallbackFactory implements FallbackFactory<UserInfoServerClient>
{
    private static final Logger LOGGER = LoggerFactory.getLogger(FeignClientFallbackFactory.class);
    
    @Override
    public UserInfoServerClient create(Throwable cause)
    {
        return new UserInfoServerClient()
        {
            @Override
            public Object usage()
            {
                UserInfoServerClientFallbackFactory.LOGGER.info("fallback;reason was:",cause);
                return new HashMap(0);
            }
        }
    }
}

二 、使用 Feign + Hystrix 访问需要密码认证的接口

1、去掉 UserInfoServerClient 的 @FeignClient 注解

2、创建 UserInfoServerFactoryBeanExt 类 ,该类继承于 FeignClientFactoryBean,代码如下:

public class UserInfoServerFactoryBeanExt extends FeignClientFactoryBean
{
    @Override
    protected Feign.Builder feign (FeignContext context)
    {
        Feign.Builder builder = super.feign(context);
        builder.requestInterceptor(new BasicAuthRequestInterceptor("admin","admin"))
                .logLevel(Logger.Level.FULL).logger(new Logger.ErrorLogger())
                .target(UserInfoServerClient.class,"http://user-info-server/");
        return builder;
    }
}

3、创建 UserInfoServerClientExt 类,并将其注册成为 Spring Boot 组件

@Component
public class UserInfoServerClientExt
{
    UserInfoServerClient adminClient;
    public UserInfoServerClientExt (ApplicationContext context)
    {
        this.adminClient = new FeignClientBuilder(context).forType(UserInfoServerClient.class, new UserInfoServerFactoryBeanExt(),"user-info-server").build();
    }
    public UserInfoServerClient getAdminClient()
    {
        return this.adminClient;
    }

}

4、在接口上使用 @HystrixCommand(fallbackMethod = "usageFallBack") 注释,表示当接口发生错误时,将执行该方法。

4、自动注入 UserInfoServerClientExt 即可使用 UserInfoServerClient 访问需要认证授权的接口

三、其他

1、为 Feign 禁用 Hystrix

1、为指定 Feign 客户端禁用 Hystrix

  • 新建一个 Feign 配置类,代码如下

    @Configuration
    public class FeignDisableHystrixConfiguration
    {
        @Bean
        @Scope("prototype")
        public Feign.Builder feignBuilder()
        {
            return Feign.builder();
        }
    }
    
  • 在想要禁用 Hystrix 的 @FeignClient 引用该配置类即可,例如

    @FeignClient(name = "user", configuration = FeignDisableHystrixConfiguration.class)
    public interface UserFeignClient
    {
        
    }
    

2、全局禁用 Hystrix

  • 在application.yml 中配置 feign.hystrix.enable = false 即可。
posted @ 2020-12-02 15:23  zolmk  阅读(394)  评论(0编辑  收藏  举报