返回 登录
0

微服务-不仅仅是写代码

原文:Microservices - More Than Writing Code
作者:Bilal Wahla
翻译:lloog

译者注:作者介绍微服务架构的配置管理和各种模式。

了解微服务架构的细节,如配置管理和各种模式,这对于微服务的成功至关重要的。

众所周知微服务带来了的高质量服务架构,其中包括了模块化、粒度、可重用性、可扩展性、可测试性和可维护性等属性。因为微服务自身实现的难度和复杂性,所以微服务并不是一个可以简单实现的架构。在这篇文章中,我将努力讲解一些我掌握的以及 过去我设计与实现的几个基于Java / Groovy & Spring框架的微服务项目中用到的技术。

配置管理

每个微服务,都是松散耦合的,独立可实现的、可测试的、可部署的、可维护的,都有自己独特的配置。微服务的独特配置包括与数据库或第三方服务以及其他内部微服务的集成。在没有版本控制和代码审计的情况下改变配置意味着可变服务器(每个代表一个微服务器)改变配置要手动并且耗时的。只有隔离、集中、分布式和高可用性的配置管理,才可以管理由微服务组成的系统的配置,例如 Spring Cloud Config或HTTP,用于外部配置(键值对或等效的YAML内容)的基于资源的API等。利用Spring Cloud Config实现配置服务器只需添加Spring Cloud Config依赖,即在主类上的添加@enableconfigserver注解和一个指向类似GitHub的版本控制库的配置文件。任何微服务都可以简单地添加Spring Cloud Config客户端依赖到他们的架构中。

路由模式

服务发现

当你有运行多个实例的微服务时,其中每个实例都是根据微服务需求变化情况进行缩放,因此服务客户端不需要知道服务的IP和端口。那么如何进行交互呢,解决方案是使用一个高可用性、负载均衡、弹性和容错的服务发现。让IT运营团队在基础架构层面上做到这一点,意味着要为业务和维护提供额外的工作,这就偏离了DevOps和持续交付这一组极其重要的微服务价值观。

像配置服务器一样,发现服务器通过在发现服务器应用程序的主类上使用Spring Cloud Eureka依赖项和@enableeurekaserver注解,就可以很简单的设置。通过添加Spring Cloud Eureka的依赖和在其主类上使用@enableeurekaclient注解,发现服务器的客户端可以很方便地使用这个服务器。当一个服务发现客户端服务的实例出现时,它会用服务发现注册它的IP地址,并发送一个心跳。这意味着通过服务发现知道什么时候它的客户端已经终止,然后删除已经终止的实例的IP。如果发现服务器被扩展,则所有节点都共享每个客户端服务的所有实例的健康信息。

服务网关

将关注点分离并作为微服务实现它们仍然会给我们带来一些在每个微服务中都必须发生的事情。这些横切点主要包括静态和动态路由、身份验证和授权[使用Spring Cloud Security / OAuth2 / JWT]、度量采集、审核和日志[使用Spring Cloud Sleuth]。这些应该在一个地方实现,而不能在多个微服务(由多个团队)复制(可能被损坏)。这有个解决方案,在微服务应用程序和外部世界之间,使用Spring Cloud / Netflix Zuul的服务网关接收任何微服务的入站请求:

  1. 通过服务发现得到的自动映射路由将传入的呼叫映射到下游服务。

  2. 你需要编写自定义逻辑,该逻辑将应用于流经网关的所有服务调用。Netflix Zuul允许你在网关中使用过滤器。两个主要的过滤器,一是预过滤器,使用Spring Cloud Security / OAuth2 / JWT的身份验证和授权,二是后置过滤器,用于使用Spring Cloud Sleuth进行日志记录。

如你对Spring期望的那样,设置Zuul服务器变得很简单,只要在类路径上添加依赖,在主类上添加@ enablezuulproxy注解就可以了,同时你的服务网关服务也已经准备好了。当然,你还可以按照你的意愿配置应用额外的功能或定制行为,例如,可以使用发现服务或者默认服务ID查找服务,也可以根据这些服务ID定义映射,这会使你的服务网关的URL更精简。

客户端弹性模式

各种微服务器通过良好的路由模式进行交互,这是很好的,但往往我看到一个服务客户端崩溃不是由于自己的错,而是服务本身,如服务逐渐退化,运行缓慢,并使服务客户端运行缓慢,随后降低整个应用程序的性能。客户端弹性应该作为服务客户端和服务之间的保护层。为了使服务客户恢复弹性,应该实现各种模式,接下来举一些例子:

断路器模式

微服务被执行来监视一个调用,如果调用花费太长时间,则应该拦截并终止它。微服务应该监视所有服务的调用,如果大量的调用失败达到一定程度,断路器就会跳闸。

回退模式

如果可能的话,应该为替代资源或排队等待进行后续处理。

舱壁

隔板将各个远程调用分组到各自的线程池中,防止一个缓慢的服务调用影响其他线程池。

下图中的每一个微服务(紫色框)都在向数据库或其他服务发出远程调用,出于这个原因,使用Spring Cloud / Netflix Hystrix实现了这些客户端弹性模式(注意断路器图标),以防止整个系统在出现问题时崩溃。在类路径中使用Spring Cloud / Netflix的Hystrix依赖,在主类上使用@ enablecircuitrcuitbreaker注解,在进行远程调用的方法上使用@ hystrixcommand注解,所有这些都可以使用上面的模式(详细信息请参阅API文档)。

image

结论

将上述所有内容组合到一个包含两个服务的应用程序中,A服务和B服务(由身份验证服务保护),为了获取额外的信息,A服务与B服务(通过服务网关)进行通信,并对请求进行响应。当你实现一个微服务体系结构,但不采用上面的模式,意味着你已经开发了一个模块化的系统(从我的经验来看,无论总体架构的选择如何,模式始终是非常重要的),但在这种情况下还会带来额外的复杂性。

评论