0%

微服务(不是最佳)实践

目的

本篇文章主要根据作者的一些实践来阐述和总结微服务的商业价值、设计原则和技术优势。

什么是微服务

传统企业以烟囱形式交付软件。这些软件都是由各部门的各自需求产生的。软件的开发和采购都在这个有限的需求范围内展开。另一方面,面向客户的业务流程通常跨越多个部门。这两种需求之间缺乏一致性会导致工作重复,以及在每个解决方案中丢失或产生不准确的信息。后者是企业集成的主要目标。

服务的概念是将面向客户的业务流程视为解决方案的要求演变而来的。 IT部门可以灵活地响应变化,从而满足变更现有流程或发明全新流程的需求。服务不是开发或采购传统意义上的“软件”,而是可以解决业务流程的自动化需求。

微服务设计基本原则

微服务功能使用面向业务的API形式对外表示。它们封装了核心业务能力,因此是业务的资产。服务的实现是完全隐藏的,因为接口是纯用业务术语定义的。

重视服务对企业的业务价值,促进它们在多种情况下的适配性。相同的服务可以将其功能交付给多个业务流程或不同的传统/数字化业务渠道。

通过松耦合设计原则,应该最小化服务及使用者之间的依赖关系。通过对面向业务的API契约进行定义,消费者不会受到服务实现细节变更的影响。这允许服务在修改隐藏在接口背后的逻辑或者服务组合时,并不会对下游产生任何影响。

服务自治是实现微服务中对运行环境和数据库的重要度量标准。它提高了识别微服务的性能和可靠性的标准,通过考虑微服务所满足的业务中所交换的数据(领域模型),可以帮助你识别微服务的职责范围。例如,在医疗保险行业中,企业可能需要患者、病情和理赔信息。在电子商务环境中,企业可能需要订单、商品、折扣或客户信息。在金融解决方案中,可能有转帐、账户、收款人。职责应该精简和集中。微服务不是整个后端系统的抽象,而是系统中负责存储那一部分业务实体的系统。服务的无状态性,还有助于服务的整体可用性和可伸缩性。

复用是微服务设计的一个重要原则。但是,复用的范围需要缩小到业务中的特定领域。

所有这些设计原则构成了可组合性原则,可组合性原则允许服务在不同上下文中向业务交付价值。它与其他服务组合形成新的服务聚合,这实际上是应用软件开发的新形式。

服务发现的目的是让所有相关方清楚地了解微服务的业务目的和接口规范。因此,服务的发布必须确保调用方的开发人员能够轻松理解和使用它。

面向业务领域的微服务架构

微服务设计的重点是要针对特定领域进行设计,而不是对业务的每个方面都考虑到位。业务的实际情况是,在各个业务单元或子领域中,对业务实体的理解有很大的不同。

如果每个领域对同一概念有不同的理解,就不应该尝试设计企业范围的服务。举个例子,客户这个领域实体在客户服务、订单、发票和运输领域都存在,但业务概念不尽相同。

微服务与单体架构

微服务是IT处理软件开发方式的一个根本性转变。传统的软件开发过程(瀑布式开发、敏捷开发等)通常会导致相对大型的团队在单个、独立的系统上工作。项目经理、开发人员和运营人员通力合作构建一个单体应用。然而传统方法有几个关键问题:

  1. 单体应用可能会演变成一个“大泥球”;没有一个开发人员(或一组开发人员)了解整个应用的每个细节。当高级开发人员退出一个项目,并由初级或外包人员替代以进行维护时,这个问题会加剧。
  2. 有限的复用性。单体应用隐藏了它们的内部特性。虽然某些可复用性可以通过API实现,但内部组件的复用是有限的。当实现复用时,通常是通过共享库来实现的,这些共享库加剧了耦合性。
  3. 扩展单体应用很困难。由于将所有功能捆绑在一个部署单位中,因此通常不可能调整应用的特定功能而不影响其他功能。单体应用通常很难做到动态伸缩。
  4. 在频繁部署单体应用时,很难实现操作的敏捷性。虽然操作自动化可以减轻部署这些应用的大部分人肉操作,例如通过自动执行Docker配置或自动配置网络,但因为会有应用整体停机情况,开发人员不得练就强大的心理素质和厚脸皮。最糟糕的情况(不用装了,你肯定锅过~),每次部署失败或遇到生产问题时,开发人员和运维人员都会承受巨大压力。
  5. 单体应用是使用单个技术栈(如J2EE或.NET)实现的。它剥夺了程序员们使用正确(或自我感觉正确)开发语言及工具完成特定任务的机会。例如,在单体应用中,想用Rust实现J2EE应用的一部分功能是基本上不可能的。

相反,将整体分解为一组独立的服务,这些服务分别进行开发,部署和维护。具有以下优点:

  1. 微服务要体现,不仅是系统范围,还有团队规模。最好是由少数开发人员构建,可以参考“两盒披萨原则”。这意味着单个微服务的体制可以是一个小团队甚至一名开发人员。
  2. 如果微服务使用标准协议(如REST-ful API或AMQP)公开它们的接口,那么它们可以被其他服务和应用使用,而无需通过语言绑定或共享库进行直接耦合。服务注册中心可以帮助其他组发现这些服务。
  3. 微服务作为独立的部署单元存在,并且可以独立于其他服务进行扩展。
  4. 单独开发微服务允许开发人员为手头的任务使用合适的(装X的)开发语言和框架。
  5. 项目团队可以很容易地发现可复用的服务。这些服务应该提供文档、测试用例等,复用要比从头构建容易得多。

当然从事软件研发一定要牢记没有银弹这句定理,一项新技术带来灵活性同时肯定会伴随着复杂性等问题,例如:

  1. 大规模管理众多分布式服务是相当困难的。需要引入服务治理的方法及工具。
  2. 需要密切监控服务之间的相互依赖关系。服务停机、服务中断、服务升级等都可能产生连锁的下游影响,应主动分析这种影响。

避免单体式微服务

新架构带来的风险是它们被视为解决IT问题的灵丹妙药,务必不要只考虑使用“最新的技术”,而不适当考虑组织的IT现状,基础架构和开发人员技能等先决条件。微服务策略应采取谨慎,可衡量的方法,来让组织获得最大价值。建议使用面向领域设计的方法来构建你的微服务。

如果不考虑组织现状,最终将构建成一个个的单体式微服务。换句话说:将一个巨大的单体应用生硬拆分成了多个更加复杂的独立部署单元,调用的复杂性增加,投资的总体回报会减少甚至根本就是白折腾。还要注意建立持续交付的严格纪律规范,并搭配用于自动化CI/CD的必要工具。缺乏DevOps风格的团队协作和自动化肯定会给你实施过程带来更多的麻烦。

坚持原创技术分享,您的支持将鼓励我继续创作!