假设有这样一种情况:你有一个对你的业务十分重要的复杂单体系统,你已经阅读过相关的文章,希望将这一系统迁移到更加先进的、使用微服务和容器的平台上,但又不知道从何入手


如果你正面临着这一问题,那么这篇文章一定会帮到你。接下来,我将从最佳实践以及需要关注的领域两个方面,帮助你将单体应用程序演进为面向微服务的应用程序。


概述


毋庸置疑,完全从头做起的、从基于容器的云服务开始入手的“绿地开发模式(Greenfield Development)“是最理想的开发模式。然而,对大多数开发团队而言,这并不现实。大多数开发团队要为多个已经存在几年的应用程序提供支持,并且需要利用现代工具集和平台对它们进行重构,这通常称为”棕地模式开发(Brownfield Development)“

并非所有的应用程序技术都可以轻松放入容器。我们可以通过一番工作让现有的应用去适应容器,但疑问也随之而来:这样做是否真的值得?例如,你确实可以将整个大规模的应用程序迁移到容器或者云平台上,但这么做真的可以明显地提高灵活性或是降低成本吗? 


评估所有现有组件



对应用程序的当前状态及其基础堆栈进行评估,这听起来并非一个革命性或创造性的想法,但是当你完整评估了所有的网络和基础架构组件之后,可以说你已经取得了阶段性的成功。你未必必须直接涉及应用程序的核心,小而渐进式的步骤才是让你的合作伙伴和支持团队更轻松地使用容器的最佳方式


举一些容器友好的基础架构组件案例:Web服务器(如Apache HTTPD)、反向代理和负载均衡器(如haproxy)、高速缓存组件(如memcached)、甚至是队列管理器(如IBM MQ)。

假如你处于这样一种极端的情况:如果应用程序是Java编写的,那么可以让更轻量的Java EE容器在Docker中运行而不需要拆分应用程序吗?对这一问题,WebLogic、JBoss(Wildfly)和WebSphere Liberty是适用于Docker的Java EE容器的绝佳案例。


厘清现有应用组件


现在,基础设施层的容器已经开始运行,现在可以在应用程序内部查找组件的逻辑分解。例如,用户接口是否可以作为单独的可部署应用程序分割出来?一部分的UI是否可以绑定到特定的后端组件并单独地部署(比如带有结算业务逻辑的计费界面)?


在将应用程序组件组合成为单独的工件时,有两个重要的注意事项:


1、在单体应用程序中,总有一些共享库,它们会在一个新的微服务模型中被多次部署。多次部署带来的好处是每个微服务都可以遵循它自己的更新计划。仅因为一个公共库有新的特性,并不意味着每个人都需要它,且每个人都必须立即升级。

2、除非有一种非常明显的方式来分开数据库(如多schemas)或者该特性跨越多个数据库,不然的话就放弃它。单体应用程序倾向于交叉引用表,并构建典型的“属于”一个或多个其他组件的自定义视图,因为原始表是现成的,在时效上是公认的快。


下一步:业务改进


如果到这一步你已经完成,取得了一些进展,并且可能已经确定了可拆分成单独可部署工件的应用程序组件,那么现在是时候将业务改进作为你的首要发展道路,将应用程序重新设计为更小的基于容器的应用程序,这些最终将成为你的微服务。


如果你已将账单作为想要从主应用程序拆分出来的第一个区域,那么就需要完成与那些应用组件相关的所需增强功能和bug修复。一旦你已经准备好发布,将它们部署上去,并且将分离包含在发布版本中。


随着对应用程序的不断剥离,你的团队将会更加熟悉如何拆分组件,并且将它们放入自己的容器中。


结  论 


当将单体应用程序分解并部署为一系列使用容器的小型应用程序时,它将在效率上达到一个新高度。根据实际负载(而不是简单的构建峰值负载)独立扩展每个组件,更新单个组件(无需重新测试和重新部署所有内容)将大大缩短花费在QA上以及获得变更管理的批准的时间。由此可见,在容器上运行不同功能的小型应用会是未来(更有效)的方式