亚马逊AWS官方博客
白皮书:Amazon EC2 Container Service(ECS) 上的微服务架构(上篇)
简介
微服务是一种软件开发的组织和架构方法,它可以加快软件交付周期、增强创新和自主性,提高软件的可维护性和可伸缩、可扩展性,同时也提高了企业开发和发布软件服务的能力。使用微服务架构,软件产品将由多个独立的、可通过API进行交互的服务组成。这些服务将由各个小团队独自负责。
通过本白皮书,我们将首先总结一下微服务架构的特性,讨论构建微服务架构面临的挑战和难题,然后介绍AWS的ECS容器集群服务,以及如何利用ECS结合其他AWS提供的服务解决微服务架构中遇到的难题。
什么是微服务架构
微服务架构的特性
近些年,微服务架构的概念变得越来越火[i],事实上微服务并非某项具体的技术或框架,它也不是软件工程学中新的概念,而是一些成功的,经过实践论证的概念的组合,比如面向对象方法论、敏捷开发、面向服务架构、API-first设计、以及持续集成。
“微服务”这个名词是一个概括性的术语,很难对其进行精确的定义。但是所有微服务架构方法都具有以下共同特性:
- 去中心化:微服务架构是由去中心化数据管理的分布式系统组成。它不依赖中心数据库上统一的数据库模式。每一个服务都有自己独立的数据模型。去中心化的另一个含义是,每个服务在开发、部署、管理和维护过程中也是相互独立的,不依赖某个中心系统。
- 独立:微服务架构中各个服务组件都可以独立进行更改、升级和替换,而不会影响其他服务组件的正常功能。同样,负责各个服务组件的团队之间也都是相互独立的,互不干扰的。
- 专注做好一件事:每个服务组件都是专注于某个问题域的功能集合,一旦某个服务复杂度到达一定程度,则应该考虑将其进行服务切分或对其进行再次微服务架构。
- 多语种:微服务并不是“一体通用”的方法,它允许各个团队根据自己的喜好选择最适合自己问题域的开发语言、开发工具。因此,微服务无论在操作系统、开发语言、数据存储还是工具,都是兼容的。也就是说,微服务是“多语种”的。
- 黑盒子:微服务中的服务都是按照“黑盒”设计的,也就是说,它们将内部逻辑对外隐藏进来,各个服务间通过定义良好的API进行通信,避免了暗含的相互依赖。
- 谁构建,谁运行:通常情况下,在生产环境中,构建了某个服务的团队负责该服务的运行和维护。这条规则也称之为DevOps[ii]。DevOps除了能让各个团队按照自己的安排独立工作外,还可以让开发人员更贴近软件产品的真正使用者,能帮助他们更好地了解用户的需求。微服务对于企业组织架构上的影响也是不容忽视的,正如康威定律所言,系统架构是公司组织架构的反映[iii]。
图1:微服务架构的特征
单体型架构 vs. SOA vs. 微服务架构
技术为业务而生,架构也为业务而出现,无论传统单体型架构、SOA和微服务都是因为业务的发展而出现。出现SOA以及微服务框架与业务的发展、平台的壮大密不可分。
单体型架构
当网站或者应用流量很小时,只需一个应用,将所有功能都部署在一起,以减少部署节点和成本,简化开发流程,适合于个人开发或者小团队开发一些功能单一的小产品使用。这是最传统的架构模式,一般整个系统都是有一个统一的数据中心,各个功能模块显式进行相互依赖(比如直接调用模块公开的方法)。当网站流量随着业务发展不断变大时,这种架构的应用在可扩展性、容错性(一旦某个功能模块被流量击溃,整个系统瘫痪)上存在致命性的缺陷。
SOA
当网站或者应用流量变大,单体型架构无法招架之时,可以采取面向服务架构方式,将应用根据系统维度、功能维度、读写维度或者模块维度进行划分成各个独立的服务组件,服务组件间通过某个约定的方式(比如Web Service或者HTTP REST API)进行通信。当服务越来越多,容量的难以准确评估,小服务导致资源浪费等问题逐渐显现,此时需增加一个调度中心基于访问压力实时管理集群容量,提高集群利用率,这种架构一般仍然存在一个统一的数据中心或者调度中心。整个系统的可维护性、可扩展性相对于单体型架构得到提高,但在服务细粒度、隔度性、去中心化方面仍与微服务有差,另外就是SOA架构常常依赖于总线结构,利用可热插拔的中间件以及消息队列来完成服务与服务之间的解耦,对于总线结构的依赖也使得服务的独立性并没有被完全剥离。
微服务架构
在微服务架构中,每个服务都要去中心化,不存在单点故障问题。每个服务都要实现高可用、高负载,不会因为一个服务不可用而影响整套业务流。每个服务细粒度,专注于自己的问题域,与别的服务采用更好的Restful或者良好定义的API进行通信。服务都要高度通用化,即多种终端都可调用,不分语言和平台服务部署或升级简单,不会消耗大量人力并且部署过程不易出现人为错误,同时还具有快速注册与自动服务发现功能。
微服务的益处
许多AWS客户选择微服务架构来解决传统单体型架构中存在的敏捷性和可扩展性限制的问题。让我们来看看选择微服务架构能够带来哪些方面的益处吧。
敏捷
使用微服务的组织由多个负责运维独立服务的小团队组成。各个团队都是在界限明确的小范围内独立、快速地工作,从而起到减小迭代时间的效果。各个小团队效率的提升将使整个企业组织工作效率进行很大程序地提高。
图2标示由多个小团队组成的企业组织架构与由一个大团队组成的企业组织架构,在发布部署一个应用时的工作效率区别。
图2:部署微服务
创新
小团队可以独立自主地针对自己负责的问题域选择相关的技术、框架和工具,这就是创新的体现。职责与义务,让团队产生对自己的服务的责任感。
DevOps通过将开发与运维人员结合到一个团队中,让他们能更早地、更好地沟通,解决了开发部署过程中没必要的摩擦和矛盾。当应用程序部署时,敏捷的处理流程可以让开发和运维工作不再需要暂停下来,相反,整个软件交付周期,从提交代码到发布版本,整个流程将变成自动化的。测试一个新的想法,或者当新功能出现问题时及时回滚,将变得更加轻松。因为失败成本的降低,团队将更加乐于更改和创新。
质量
使用微服务架构您的应用程序,将一定程度上提高代码质量。这跟面向对象设计中提出的分模块开发有同样的效果:提高代码的可重用性、封装性和可维护性。
伸缩性
细粒度解耦的微服务架构另一个好处就是,它非常适合构建大规模系统。它允许针对不同的服务选择最适合的技术,这也是性能优化的体现。每个服务都可以使用最合适的开发语言和框架来实现,利用最优的数据持久化解决方案,并通过各自独立的服务配置进行调优。
合理解耦的微服务架构,可以独立地进行水平伸缩扩展。这相对于传统架构中使用的垂直伸缩有很大的优势。垂直伸缩指的是当业务量、流量增大时,升级硬件资源,将应用部署到“更大的机器”上,这会导致“机器硬件资源上限”和伸缩时宕机的问题。水平伸缩,通过将更多的服务部署到服务池(多个机器组成的集群)中,可以动态地适配流量,并且不会陷入单个机器资源上限问题。整个水平伸缩的过程将会是自动化的。另外,应用程序的可靠性将得到增加,因为出现问题的服务可以自动地被健康的服务替换掉,而不影响整个应用的运行。
可用性
微服务架构可以轻松实现故障隔离。通过健康检查、缓存、隔离仓、断路器等技术,可以减小当某个组件出现故障时的影响,从而保证应用的高可用性。
微服务架构面临的挑战
尽管拥有前面提到的那么多优点,但是微服务架构和所有其他架构一样,都不是解决所有问题的“银弹”。使用微服务架构也会面临一些挑战和难题。比如:
- 微服务架构都是分布式的,也就会存在所有“分布式计算误区”中提到的问题[iv]。
- 从单体型架构迁移至微服务架构,需要您准确地划分好各个服务间的界限,并且从应用层到数据库层松耦合代码依赖。
- 除此之外,在组织管理方面还存在着一些挑战,比如如何组建一个高效的团队,如何将团队转变成DevOps的生产模式,如何合理化开发团队与运维团队的沟通等。
本白皮书主要关注的是架构和运维方面遇到的挑战,如果想了解更多关于AWS如何运用DevOps的知识,请访问https://aws.amazon.com/devops[v]
架构复杂度
在传统单体型架构中,所有的复杂度和依赖都存在项目的代码库中。而对于微服务架构而言,复杂度变成了各个服务间的交互。
在架构上面临的挑战有处理异步通信、连锁故障、数据一致性问题、服务发现和授权认证等问题。
运维复杂度
运用微服务架构,你不再只是运行一个服务,而是数十个,甚至数百个服务。这也就带来了以下问题:
- 如何以可伸缩、低成本的方式配置好所需要的资源?
- 如何避免不同的团队重复“造轮子”,重复处理同一个问题,或重复安装配置相同的软件工具?
- 如何跟踪并管理好上百个代码流的部署过程和它们之间的相互依赖(不同服务可以单独部署)?
- 如何监控整个系统的健康并提前感知潜在的热点和流量高峰?
- 如何在整个系统各个服务间追踪和调试问题?
- 如何分析一个快速增长并超出预期需求的分布式系统的海量日志数据?
- 如何处理不同技术栈、开发环境间缺少统一标准的问题?
- 如何受益于不同技术带来的开发效率,而不受困于维护升级这些技术带来的困难?
微服务与云平台
微服务近些年的崛起与诸如AWS这样的公有云平台的发展密切相关。AWS提供了可以直接解决微服务架构面临的挑战的服务。
- 按需资源调配:资源可以快速根据资源进行配备。相对于传统的基础设施,云平台几乎可以说在资源上是没有上限的。运行于不同环境、不同版本的服务可以临时或永久地共存。不同需要进行困难的资源预测和评估。按需资源调配解决了如何以可伸缩、低成本的方式配置好所需要的资源的问题。
- 低成本低风险地进行尝试:你只需为你使用的资源付费,从一定程序上降低了你尝试新想法的成本。新功能或者新服务可以快速地发布,并且当尝试失败时,可以快速关闭这些服务和其所需的资源。降低尝试新想法所需的成本和风险,将大力推动更多的创新。这也是跟微服务架构提倡的高度敏捷相符合。
- 可编程性:AWS服务自带API、命令行工具(CLI)和针对不同语言的SDK。服务器甚至整个架构都可以通过编码的方式进行克隆、关闭、扩展、监控并且在发生故障时实现自动恢复。标准化和自动化是构建速度、一致性、重复性和可伸缩的关键。你可以通过编码的方式统一管理你所需的资源,减少运维微服务架构所需的精力。
- 基础设施即代码:除了可以编写脚本来配置和管理你的资源,AWS还支持你将基础设施代码化,像应用程序的代码一样放置到版本管理工具中进行管理。因此,各个版本的基础设施都可以随时进行重新部署。你可以保证基础设施代码与应用程序代码一样的质量和性能。回滚不再只与代码相关,也包含整个基础设施。可编程性和基础设施即代码可以解决运行、维护、扩展微服务架构时面临的问题。
- 持续交付:云平台的可编程性推动了配置和部署流程的自动化。开发阶段的持续集成概念也因此可以扩展到运维阶段(因为运维也是可编码的了),从而形成持续集成与交付的概念。持续交付解决了如何同时管理多个代码流并行部署交付的问题。
- 自我管理的服务:云平台最出色的优点就是服务都是自我管理的。你不再需要进行繁重的配置虚拟机、安装配置优化软件、处理资源伸缩扩展、管理备份等运维工作。诸如监控、安全、记录日志、伸缩和保持可用性等系统操作和特性都在云平台服务中内置好了。自我管理的服务从一定程度上缓解了运行微服务架构的复杂度和工作量。
- 面向服务:AWS本身就是微服务架构的。每一个AWS服务都是针对某个特定问题域的,并且都是通过API进行相互通信。你可以将这些服务像乐高积木一样组合成复杂的结构,用来解决特定的问题。这样就解决了重复“造轮子”的问题。
- 多语种:AWS提供了多种存储得数据库技术供你选择。AWS Marketplace上有许多可以运行在EC2上的操作系统供你使用。AWS的SDK支持各种各样主流开发语言。这可以让你根据特定问题选择最合适的技术方案,从而避免重复“造轮子”问题。
引用
[i] https://www.google.com/trend/explore#q=Microservices
[ii] https://en.wikipedia.org/wiki/DevOps
[iii] https://en.wikipedia.org/wiki/Conway%27s_law
[iv] https://en.wikipedia.org/wiki/Fallacies_of_distributed_computing
[v] https://aws.amazon.com/devops/
白皮书:Amazon EC2 Container Service(ECS) 上的微服务架构(下篇)
更多白皮书:https://aws.amazon.com/cn/whitepapers/
观看在线研讨会视频-运行在Amazon ECS上的微服务架构及实践
作者介绍
李磊,AWS解决方案架构师,负责基于AWS的云计算方案的架构设计,同时致力于AWS云服务在国内和全球的应用和推广。在大规模并发后台架构,电商系统,社交网络平台、互联网领域应用,DevOps以及Serverless无服务器架构等领域有着广泛的设计与实践经验。在加入AWS之前超过十年的开发和架构设计经验, 带领团队攻克各种技术挑战,总是希望站在技术的最前沿。