天天看点

使用Hystrix 、Feign 和 Ribbon构建微服务-spring cloud 入门教程

可能你读过一些关于 Hystrix 的文章,你知道它的用途是什么。今天我想向您展示一个具体如何使用它的示例,它使您能够与来自 Netflix OSS 堆栈的其他工具(如 Feign 和 Ribbon)结合使用。我假设您对微服务、负载平衡、服务发现等主题有基本的了解。如果没有,我建议您阅读一些关于它的文章,例如,我对微服务架构的简短介绍可在此处获得:使用 Zuul、Ribbon、Feign、Eureka 和 Sleuth、Zipkin 创建简单spring cloud微服务用例-spring cloud 入门教程。那篇文章中使用的代码示例有助于你快速了解本文。

让我们看一些使用回退和断路器的场景。我们有客户服务,它从Account Service调用 API 方法。有两个正在运行的Account Service实例。对Account Service实例的请求由 Ribbon 客户端 50/50 进行负载平衡。

使用Hystrix 、Feign 和 Ribbon构建微服务-spring cloud 入门教程

场景一

对 Feign 客户端 (1) 禁用了 Hystrix,对本地实例 (2) 和其他实例 (3) 上的 Ribbon 客户端禁用了自动重试机制。功能区读取超时比请求最大处理时间 (4) 短。这种情况也发生在没有 Hystrix 的默认 Spring Cloud 配置中。当您调用客户测试方法时,您有时会收到完整响应,有时会收到 500 HTTP 错误代码 (50/50)。

ribbon:
  eureka:
    enabled: true
    MaxAutoRetries: 0 #(2)
    MaxAutoRetriesNextServer: 0 #(3)
    ReadTimeout: 1000 #(4)

feign:
  hystrix:
    enabled: false #(1)
            

场景二

对于 Feign 客户端 (1) 仍然禁用 Hystrix,在本地实例 (2) 上为 Ribbon 客户端禁用自动重试机制,但在其他实例上启用一次 (3)。您总是会收到完整的回复。如果您的请求由具有延迟响应的实例接收,它会在 1 秒后超时,然后 Ribbon 调用另一个实例 - 在这种情况下不会延迟。您可以随时更改

MaxAutoRetries

为正值,但在该示例中没有给我们任何内容。

ribbon:
  eureka:
    enabled: true
    MaxAutoRetries: 0 #(2)
    MaxAutoRetriesNextServer: 1 #(3)
    ReadTimeout: 1000 #(4)

feign:
  hystrix:
    enabled: false #(1)
            

场景3

这里不是一个非常优雅的问题解决方案。我们设置

ReadTimeout

的值大于 API 方法中的延迟(5000 毫秒)。

ribbon:
  eureka:
    enabled: true
    MaxAutoRetries: 0
    MaxAutoRetriesNextServer: 0
    ReadTimeout: 10000

feign:
  hystrix:
    enabled: false
            

一般来说,场景 2和3 的配置是正确的,你总是得到完整的响应。但是在某些情况下,您会等待超过 1 秒(场景 2)或超过 5 秒(场景 3),并且延迟实例收到来自 Ribbon 客户端的 50% 请求。但幸运的是,有 Hystrix——断路器。

场景 4

让我们通过删除

feign

属性来启用 Hystrix 。Ribbon 客户端 (1) 没有自动重试,其读取超时 (2) 大于 Hystrix 的超时 (3)。1000ms 也是 Hystrix

timeoutInMilliseconds

属性的默认值。Hystrix 断路器和回退将适用于帐户服务的延迟实例。对于一些第一次请求,您会收到来自 Hystrix 的回退响应。然后延迟的实例将从请求中切断,其中大部分将被定向到未延迟的实例。

ribbon:
  eureka:
    enabled: true
    MaxAutoRetries: 0 #(1)
    MaxAutoRetriesNextServer: 0
    ReadTimeout: 2000 #(2)

hystrix:
  command:
    default:
      execution:
        isolation:
          thread:
            timeoutInMilliseconds: 1000 #(3)
            

场景5

这个场景是场景 4的更高级的开发。现在 Ribbon 超时 (2) 低于 Hystrix 超时 (3),并且还为本地实例和其他实例 (4) 启用了自动重试机制 (1)。结果与场景 2和3 相同——您收到完整的响应,但启用了 Hystrix 并且它从未来的请求中切断了延迟的实例。

ribbon:
  eureka:
    enabled: true
    MaxAutoRetries: 3 #(1)
    MaxAutoRetriesNextServer: 1 #(4)
    ReadTimeout: 1000 #(2)

hystrix:
  command:
    default:
      execution:
        isolation:
          thread:
            timeoutInMilliseconds: 10000 #(3)
            

我可以想象其他一些场景。但这个想法只是在修改

application.yml

.

Hystrix

让我们仔细看看场景 4 中描述的标准 Hystrix 断路器和用法。要在 Spring Boot 应用程序中启用 Hystrix,您必须将以下依赖项添加到

pom.xml

. 第二步是向

@EnableCircuitBreaker

主应用程序类添加注释,

@EnableHystrixDashboard

如果您希望 UI 仪表板可用。

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

Hystrix 回退设置在客户服务内部的 Feign 客户端上。

@FeignClient(value = "account-service", fallback = AccountFallback.class)
public interface AccountClient {

   @RequestMapping(method = RequestMethod.GET, value = "/accounts/customer/{customerId}")
   List<Account> getAccounts(@PathVariable("customerId") Integer customerId);

}
            

回退实现非常简单。在这种情况下,我只返回一个空列表,而不是从帐户服务收到的客户帐户列表。

@Component
public class AccountFallback implements AccountClient {

   @Override
   public List<Account> getAccounts(Integer customerId) {
      List<Account> acc = new ArrayList<Account>();
      return acc;
   }

}
            

现在,我们可以进行一些测试。让我们启动发现服务,不同端口上的两个帐户服务实例(启动期间的-DPORT VM 参数)和客户服务。测试的端点是/customers/{id}。还有 JUnit 测试类,它向客户服务模块中提供的此端点发送多个请求

pl.piomin.microservices.customer.ApiTest

@RequestMapping("/customers/{id}")
public Customer findById(@PathVariable("id") Integer id) {
   logger.info(String.format("Customer.findById(%s)", id));
   Customer customer = customers.stream().filter(it -> it.getId().intValue()==id.intValue()).findFirst().get();
   List<Account> accounts =  accountClient.getAccounts(id);
   customer.setAccounts(accounts);
   return customer;
}
            

我在account-service主类上启用了 Hystrix Dashboard 。如果您想访问它,请从您的 Web 浏览器调用http://localhost:2222/hystrix地址,然后从客户服务 http://localhost:3333/hystrix.stream键入 Hystrix 的流地址。当我运行测试向客户服务发送 1000 个请求时;其中大约 20 (2%) 个转发到延迟的帐户服务实例,其余为未延迟的实例。该测试期间的 Hystrix 仪表板如下所示。有关更高级的 Hystrix 配置,请参阅其可用文档:Hystrix 简介-spring cloud 入门教程   Hystrix 原理深入分析-spring cloud 入门教程

使用Hystrix 、Feign 和 Ribbon构建微服务-spring cloud 入门教程

使用 Zuul、Ribbon、Feign、Eureka 和 Sleuth、Zipkin 创建简单spring cloud微服务用例-spring cloud 入门教程

微服务集成SPRING CLOUD SLEUTH、ELK 和 ZIPKIN 进行监控-spring cloud 入门教程

使用Hystrix 、Feign 和 Ribbon构建微服务-spring cloud 入门教程

使用 Spring Boot Admin 监控微服务-spring cloud 入门教程

基于Redis做Spring Cloud Gateway 中的速率限制实践-spring cloud 入门教程

集成SWAGGER2服务-spring cloud 入门教程

Hystrix 简介-spring cloud 入门教程

Hystrix 原理深入分析-spring cloud 入门教程 

使用Apache Camel构建微服务-spring cloud 入门教程

集成 Kubernetes 来构建微服务-spring cloud 入门教程

集成SPRINGDOC OPENAPI 的微服务实践-spring cloud 入门教程

SPRING CLOUD 微服务快速指南-spring cloud 入门教程

基于GraphQL的微服务实践-spring cloud 入门教程

最火的Spring Cloud Gateway 为经过身份验证的用户启用速率限制实践-spring cloud 入门教程

继续阅读