微服务耦合

Microservice Coupling

我正在构建一个具有微服务概念的新应用程序,但我不知道如何在不耦合的情况下与另一个微服务进行通信。这是我的场景。

我想显示一个关于我的销售的图形栏,但我有两个微服务,第一个是 sales-service,另一个是 product-服务。在这种情况下,我必须 select 我要过滤的时间段,然后 select 销售额,然后 select 来自这些销售额的产品,但我直接调用产品服务休息,如果我的产品服务失败,一切都会失败。在这种情况下,正确的工作方式是什么?

编辑

Diagram of Architecture

这是带有一些服务的架构。问题是销售服务必须与其他服务通信以获取一些信息。

我们有数百个客户端的销售软件,这个应用程序接收这些数据,我们有一个显示这些信息的前端。在这种情况下,微服务是最好的方法?

我正在使用 Spring 云。

如果您不知道如何在没有耦合的情况下进行通信,那么显而易见的答案就是不进行通信。

我是认真的。您应该以不需要与其他服务同步通信来完成业务案例的方式设计您的服务。如您所述,否则会导致运行时耦合。

显然,如果您有 "product-service",那已经表明这是几乎所有其他服务都需要的东西。您通过以特定方式将其分解,将耦合融入架构中。

特别是在这种情况下:"sales" 服务应该拥有报告的所有数据,因此它不必进行通信。您可能会发现其他地方实际上不需要此数据,因此不会有真正的数据重复。

看看这些家伙:http://scs-architecture.org/。他们有很多好主意如何(以及为什么)避免这种耦合,以及如何设计独立的服务,或者至少只 "offline" 个依赖的服务。

显然这并不适用于所有情况。最值得注意的是 Netflix 正在进行耦合和 "synchronous" 调用,这就是为什么他们拥有用于此类事情的所有很酷的框架。但他们也有特定的用例,可能与您的不同。

如果不深入探讨在单体应用程序与微服务架构之间进行选择的细节,您的图表缺少注册和发现服务,例如 Spring Cloud Netflix Eureka 或 Consul。

服务会向 Eureka 注册,然后从 Eureka 获取其他服务元数据(主机、端口服务监听)。

可以在 Microservices Registration and Discovery using Spring Cloud, Eureka, Ribbon and Feign 上找到详细的教程,这是我前几天发布的博客 post。

由于您使用的是 spring 云,因此您可以轻松地与 Hystrix 断路器集成以处理微服务故障转移场景。
使用 hystrix 命令进行服务中断。

@HystrixCommand(fallbackMethod = "reliable")
  public List<String> readingList() {
    URI uri = URI.create("http://product-service/product");

    return this.restTemplate.getForObject(uri, String.class);
  }

  public String reliable() {
    return "no product available"; // or send empty array. Arrays.asList();
  }

请在

中找到示例

https://spring.io/guides/gs/circuit-breaker/

如果您需要与 return 同步调用,通过 REST 调用的调用是一个很好的选择。如果您可以进行异步调用,则可以使用 RabbitMQ 的消息架构,例如使用 Spring AMQP。

一个好的方法是当您与第 3 方和其他服务通信时,如果您有故障转移计划,那么您的服务将继续工作。

答案是在您的应用程序中使用断路器。

这里有两个例子:

  • Netflix Hystrix
  • CircuitBreaker(来自 Spring 重试)

我目前正在使用 Spring 重试并且按预期工作。

想法是:

  • 如果对外部服务的调用在一些尝试后失败,您 return 一个默认答案并让系统恢复后再重试。
  • 一段时间后,您再次开始调用外部服务(现在可以跳转)。

这是我的 Github 中的一个示例,其中我将 @CircuitBreaker 注释与 @Recover 一起实现。

spring-circuit-breaker-example

当您需要可扩展性和灵活性时,微服务是最佳选择,

根据您当前的架构图,我可以理解您正在进行同步调用以接收数据,因此销售服务必须等待来自所有服务的数据才能获得完整结果,因此输出会有更多延迟。

另一个观察结果是微服务的可扩展性,现在似乎还没有实现?

如果您可以对微服务进行异步调用,那么您可以提高性能并在每次服务 return 所需结果后合并数据。