云原生环境下,一个微服务就是一个对外提供服务的独立单元,云原生落地的第一步就是做好微服务的治理。本节会简单介绍微服务与单体架构的区别,以及微服务架构的优点。
在公司业务发展早期,业务功能相对单一,应用程序也相对较小,单体架构可以很好地支持业务开发,构建与部署简单明了,测试相对直观,也不用过多考虑扩展的问题。随着时间的推移,业务发展逐步加速,应用程序需要不断增加新功能来支持业务增长,开发、测试、部署、扩展都会变得更加困难,单个应用程序也会越来越臃肿。同时,随着代码库规模变大,研发团队的规模也会激增,团队管理的成本不断提高,《微服务架构设计模式》一书中把此时的单体架构称为“单体地狱”。
在这种架构模式下,开发变得缓慢、低效,从代码提交到实际部署的周期被拉长,可靠的部署或功能交付将越来越困难,且系统非常脆弱,很容易因为一个小问题导致整个系统宕机。我曾遇到过因为增加了一个数据库字段,导致另一个业务线功能大面积故障的场景。
随着新技术栈的更新换代,单体架构不得不长期依赖某些可能已经过时的技术栈,当Elasticsearch已经到7.x版本时,某些团队还在使用2.x的技术栈,可想而知,在这几年间团队错过了多少高效好用的新特性。
微服务是由单体架构演变而来的。在业务早期,基本上就是由单体的一个应用支撑着各种业务功能。以电商为例,用户、订单、商品、交易、支付最开始都在一个应用中实现。随着业务规模的扩大,单体架构很难支撑业务功能的平滑扩展,同时某一个功能的迭代或故障会引起整体服务的不可用。为了降低各功能模块的耦合性,提升整体业务架构的高可用性,SOA(Service-Oriented Architecture,面向服务架构)开始盛行。微服务其实是SOA的一种演进,这个概念最早是由Martin Fowler提出的。那么什么是微服务架构呢?
Martin指出:“微服务架构是一种架构模式,它提倡将单一应用划分成一组小的服务(多个微服务),服务之间相互协调、互相配合,为用户提供最终价值。每个服务运行在独立的进程中,服务与服务之间采用轻量级的通信机制进行沟通。每个服务都围绕着具体业务进行构建,并且能够独立部署到生产环境、类生产环境中。另外,应尽量避免统一的、集中的服务管理机制,对具体的服务而言,应根据业务上下文,选择合适的语言、工具对其进行构建。”
在这段话中,重要的关键词是 多个微服务、独立的进程、轻量级的通信机制 。
Netflix是微服务的先驱,其原本的应用架构是典型的巨石应用,虽然实现了应用层面的多活,但是仍然使用单一且巨大的代码库和数据库,如果数据库宕机,整个系统都将瘫痪。Netflix认为微服务必须具备以下能力。
·关注点分离:单一职责,一个微服务不能既处理用户信息,又处理订单信息。
·水平扩展:微服务可以快速水平扩展,流量实现负载均衡。
·虚拟化和弹性计算:微服务需要能够实现自动化运维,按需创建计算环境。
Netflix根据业务拆出了很多微服务,在AWS上拥有数万个虚拟机。Netflix同时为Spring Cloud社区贡献了大量优秀的开源软件,例如Eureka、Zuul、Turbine、Hystrix等。
引用《微服务:从设计到部署》里的案例,一个好的微服务架构依赖关系可以参考图1-6。
图1-6 微服务架构依赖关系图
微服务是架构演变的一个阶段,也是云原生架构的一个要素,它有很多优点。
·每个微服务足够内聚、足够小,代码职责清晰、容易理解,开发效率高。
·微服务之间可以独立部署,互不影响,让持续部署成为可能。
·扩展性更强,每个微服务的水平扩展会更加容易和灵活,可以更细粒度地进行负载均衡数据库的扩展,而且每个微服务可以根据自己的业务需求或特性选择不同的硬件服务器。
·参照康威定律,可以根据微服务的范围和边界来组织研发团队。
·容错性大大增强,一个微服务不可用并不会让整个系统瘫痪。
·创新能力机动性强,系统不会被长期限制在某个技术栈上,更容易采纳新技术,比如Web Service可能快速演变成Dubbo、Spring Cloud。
微服务并不是解决所有问题的“银弹”,不是所有问题都可以通过微服务架构来解决。关注微服务的本质和思想比关注技术和工具本身更重要,拥抱DevOps的原则和实践,在组织架构上实现跨职能的自治团队,这是必不可少的。