微服务设计的原则:IDEALS,而不是SOLID


微服务设计的原则:IDEALS,而不是SOLID

文章插图
微服务架构
作者:DevOps亮哥
来自:DevOps探路者
一、关键点:对于面向对象的设计,我们遵循SOLID原则 。对于微服务设计,我们建议开发人员遵循IDEALS原则:接口分离(Interface segregation),可部署性(deployability),事件驱动(event-driven),可用性胜于一致性(Availability over Consistency),松耦合(Loose coupling)和单一责任(single responsibility) 。
  • 接口分离:指的是不同类型的客户端(移动应用程序,web应用程序,CLI程序)应该能够通过适合其需求的协议与服务端交互 。
  • 可部署性:指的是在微服务时代,也就是DevOps时代,开发人员需要在打包、部署和运行微服务方面做出关键的设计决策和技术选择 。
  • 事件驱动:指的是在任何时候,都应该对服务进行建模,通过异步消息或事件而不是同步调用 。
  • 可用性胜于一致性:指的是最终用户更看重系统的可用性而不是强一致性,它们对最终一致性也很满意 。
  • 松耦合:仍然是一个重要的设计问题,涉及传入和传出的耦合 。
  • 单一责任:是一种思想,它支持对不太大或太细的微服务进行建模,因为他们包含了适当数量的内聚功能 。
 
在2000年,Robert C. Martin编写了面向对象设计的五个原则 。Michael Feathers后来将这五个原则的首字母组成了缩略词,也就是SOLID 。从那时起,用于OO设计的SOLID原则就在业界被广为人知 。这五个原则是:
  • 单一责任原则(Single responsibility principle)
  • 开闭原则(Open/closed principle)
  • 里氏代换原则(Liskov substitution principle)
  • 界面分离原则(Interface segregation principle)
  • 依赖倒置原则(Dependency inversion principle)
几年前,我在给其他人讲授微服务设计时,一个学生问:“SOLID原则适用于微服务吗”,经过一番思考,我的回答是“部分” 。后面的几个月,我发现我一直在寻找微服务的基本设计原则(包含一些缩略词) 。为什么这样的问题会如此重要呢?
作为一个行业,我们已经设计和实施基于微服务的解决方案已经超过六年了 。在此期间,越来越多的工具、框架、平台和支撑产品围绕微服务建立了一个极其丰富的技术环境 。在这种情况下,一个新手微服务开发人员在面对一个微服务项目中许多设计决策和技术选择时会感到迷惑 。在这个领域,一组核心原则可以帮助开发人员更好的理解基于微服务的解决方案 。
虽然有些SOLID原则适用于微服务,但面向对象是一种设计范式,它处理的元素有类、接口和继承等,与一般分布式系统中的元素(特别是微服务)有着根本的区别 。
因此,我们提出以下一套微服务设计的核心原则:
  • 接口分离(Interface segregation)
  • 可部署性(Deployability (is on you))
  • 事件驱动(Event-driven)
  • 可用性胜于一致性(Availability over consistency)
  • 松耦合(Loose coupling)
  • 单一职责(Single responsibility)
这些原则并没有覆盖基于微服务的解决方案的所有设计决策,但他们涉及到创建现代基于服务的系统的关键关注点和成功因素 。下面对微服务的“IDEALS”的原则进行详细的解释 。
二、接口分离最初的接口分离原则是指防止面向对象中类使用“胖”接口 。换句话说,就是每种类型的客户端应该有单独的接口,而不是提供一个满足所有客户端需要的所有可能方法的接口 。
微服务体系结构风格是面向服务体系结构的一种特殊化,其中接口(即服务契约)的设计一直是最重要的 。从21世纪初开始,SOA文档就规定了所有客户端都应该遵守的规范模型和规范模式 。然而,自从SOA的旧时代以来,我们处理服务契约设计的方式发生了改变 。在微服务时代,同一个服务逻辑通常有许多客户端程序 。这就是将接口分离应用于微服务的主要目的 。
实现微服务的接口分离
微服务接口分离的目标是每种类型的前端都能看到最适合其需求的服务契约 。例如,一个移动应用程序系统调用端点,这些端点返回简短的JSON格式数据作为响应 。当另一个web应用程序需要返回完整的JSON格式数据作为响应 。与此同时,还有一个桌面应用程序调用同一个服务,但需要返回完整的XML格式数据 。不同的客户端也可能使用不同的协议 。例如,外部的客户端希望使用HTTP来调用gRPC服务 。


推荐阅读