当前位置:首页 > 数码 > 单体与微服务的技术抉择-拆分还是整合 (单体微服务架构是什么意思)

单体与微服务的技术抉择-拆分还是整合 (单体微服务架构是什么意思)

admin7个月前 (04-24)数码29

作者|AshleyDavis

译者|明知山

筹划|丁晓昀

继续之战:单体架构与微服务

随着亚马逊云科技在他们的官博中宣称他们丢弃了微服务并回归单体架构,单体架构与微服务之间的抗争再次迸发。

你对此有何看法?你是支持微服务还是单体?但我想说的是,这种辨别有点空幻,由于人们争执的只是一种虚拟的概念:微服务与单体只是整个故事的一个组成局部。

亚马逊云科技的这篇文章被视为他们(作为微服务的常年支持者)曾经回头转向单体架构的证据。

虽然文章的题目显著是为了惹起关注,但从内容上看,仿佛是关于他们从函数即服务向微服务架构(假设不是比微服务更大的散布式运行程序服务)的转变。

但在我看来,这并不关键。这只能说明,亚马逊云科技的一个团队抵赖他们尝试的架构在一段期间后不奏效,而后尝试了不同的架构,获取了更好的成果。但这又怎样?这只是好的软件开发应该教训的反常环节。

咱们都宿愿专一于最关键的事件,为咱们的客户做正确的事件,在微服务与单体的争执当选边站队只会给咱们形成阻碍。有时刻,咱们须要微服务。有时刻,咱们须要单体架构。(我还不确定我能否会须要FaaS——但我坚持开明的态度)。大少数状况下,咱们须要在两个极其之间找到平衡点。

为什么咱们惧怕微服务?

当然,与单体相比,微服务更难——我抵赖这一点。但假设你有了智能化的微服务架构,这个论点就站不住脚了。我曾经经常使用过的一些无缝集成又容易经常使用的系统就是领有良好智能化的微服务。另一方面,我曾经介入的一个最艰巨的名目是一个新鲜的大单体,简直没有智能化。咱们的日子不会由于选用了单体而变得轻松。

对微服务的惧怕有没有或许是对微服务适度炒作的反噬?是的,微服务曾经被适度炒作了。微服务不是灵丹妙药。像一切潜在的处置打算一样,它们并不实用于一切场景。当你经常使用一种失误的架构来处置某个疑问(或更蹩脚的是,控制层强迫要求经常使用失误的架构)时,我可以了解你为什么会对这种架构充溢厌恶。

能否有一局部惧怕是来自微服务早期的日子?十年前,微服务确实使开发变得愈加艰巨。但从那时起,工具敌对台曾经取得了长足的提高,如今比以往任何时刻都更容易启动智能化,给微服务开发带来愈加无缝和欢快的体验。

兴许,一局部惧怕来自对复杂性的感知,我以为这是其中很大的一局部。人们会人造而然地惧怕(或至少想要防止)复杂性。我说可感知的复杂性,由于不只仅是微服务会变得复杂,单体也会——只是期间疑问。但是,关于微服务来说,复杂性是地下的,一切人都可以看获取,咱们肯定早日加以应答。在我的BootstringMicroservices一书中,我称之为将痛苦提早,以便能够在开发环节中更容易、以更低的老本应答复杂性。

可怜的是,在现代软件开发中,咱们无法回避复杂性。咱们的运行程序正在变得越来越庞大和复杂——即使是个别的单体架构也注定会变得无比复杂。

在现代的大规模软件开发中,咱们无法防止复杂性。咱们须要经常使用工具来帮咱们控制复杂性,防止它们阻碍咱们的开发环节或压垮咱们。

为什么微服务看起来如此艰巨?

构建散布式运行程序(不只仅是微服务)须要更高的技术熟练度。控制少量的服务象征着咱们肯定领有智能化控制工具。为了了解咱们的服务在做什么,咱们还须要跟踪很多物品。随着服务之间的交互变得越来越多,了解这些信息的艰巨水平将呈指数级参与。

假定你是一个小团队或在开发一个小名目,在不须要微服务的场景中驳回了微服务,或许假设你不情愿付出构建和运转散布式系统所需的技艺和技术投入,你就不能指望从中获取良好的体验。

另一个或许的痛点是未能适外地将服务与畛域对齐。我曾见过一些微服务运行程序与技术对齐但没有与业务需求对齐,造成存在过多的服务和一个不用要的难以控制的系统。将服务分得太小,不用要地参与了系统的复杂性和难度,这是一个疑问。

假设你无法正确地将架构与畛域对齐,那么无论经常使用单体还是微服务,都将遇到重大的疑问——随着服务数量的参与,这些疑问将会被大幅加大。微服务既能带来性能方面的伸缩性,也会加大曾经存在的疑问。

这只是一个伸缩性疑问吗?

微服务的真正疑问是它们只是加大了曾经存在的疑问吗?

一个蹩脚的微服务虚现比蹩脚的单体架构蹩脚X倍(X是你的散布式运行程序中服务的数量)。随着散布式运行程序中通讯门路的指数级参与,状况甚至更糟。

假设你没有适宜的工具、技术、智能化、流程和组织来应答单体,那么你凭什么以为你可以处置好微服务?

微服务不只带来性能和开发方面的可伸缩性,也带来了艰巨水平的伸缩。假设你在构建和保养单体架构时感到艰巨,转向微服务也并不会给你带来任何好处。

微服务运行程序也是一种单体,只是服务的数量参与了、服务的大小变小了而已。假设疲于应答单体架构,却以为微服务是良方,那么请再三思。

我以为微服务不只在性能和开发方面带来了可伸缩性,也带来了艰巨水平的伸缩。微服务有它的优势,但这些优势并不是齐全收费的。

微服务的老本

微服务究竟是什么?为什么咱们要将运行程序划分为独立的服务?

微服务有许多妇孺皆知的好处:

但这些好处并非微服务的所有,咱们也须要为此付出老本:

关于任何一种工具、技术、架构或任何咱们想要经常使用的物品,咱们肯定问自己一个疑问:收益能否超越了老本?假设收益超越了老本,你将在经常使用这些技术时取得良好的体验。假设没有,你将在痛苦的光阴中渡过。

控制复杂性

微服务有许多优势,但咱们经常使用它们的真歪理由是,它们可以协助咱们控制运行程序日益增长的复杂性。

单体微服务架构是什么意思

没错,微服务不是复杂性的根源,而是处置复杂性的方法。

一切的运行程序都将变得复杂,即使是单体也无法防止。微服务为咱们提供了将复杂性合成为更小、更繁难、更易控制的构建块的工具。

微服务经过将复杂性合成为繁难而隔离的局部来协助咱们控制复杂性。咱们也可以在单体架构中做到这一点,但你须要一个纪律严明和踊跃被动的团队来坚持设计的完整性,不至于变得一团糟。

咱们可以经常使用微服务来形象和将软件组件化。当然,咱们也可以在单体架构中做到这一点,但微服务还为咱们提供了结实的组件边界,更不用说其他优势了,如独立部署和缺点隔离。

或许性频谱

我在本文一开局问了一个疑问:你是支持微服务还是单体?

回到本文的题目,这不是一个非此即彼的选用。从一个大服务(单体)到许多小服务(微服务),在它们之间还有许多其他可行的选用。

这不只是单体与微服务二选一,它们之间存在一种或许性频谱。假设你将自己固定在支持单体或微服务的立场上,就将错过它们之间丰盛的架构多样性。

你不用人为地将自己对准频谱的恣意一端。你甚至不用将自己固定在其中恣意的特定位置。 虽然 一些人想让你这样以为,但并不存在所谓的正确的立场。你选用的位置应该与你的团队、业务、名目或客户对齐。只要你可以选择应该处在频谱的哪个位置。

投资报答递减

随着你在频谱的右侧移动,你将取得微服务的好处,但向右移动也随同着老本和艰巨的参与。咱们须要确保转向微服务的老本是咱们情愿承当的。

假设你不是为了控制复杂性,不须要微服务的其他好处,或许在控制单体的智能化和技术方面存在艰巨,那么你应该尽量留在频谱的左侧。随着你须要微服务的水平的参与,应该朝着频谱的右侧接近。

随着投资报答递减,不时迈向完美的微服务乌托邦或许是不值得的,但只走其中的一局部路线或许会带来高报答。

此时咱们要清楚地意识到,咱们不须要到达(我青睐称之为)微服务乌托邦的水平才干开局享用无服务的好处。无论咱们能否到达了频谱的另一侧,咱们只需朝着频谱的右侧移动肯定水平,都会获取实际的好处!

有很多要素使咱们不想迈向完美的微服务。(首先,谁来选择完美的定义?)当咱们开局向右侧推动时,将看到渺小的报答。但随着继续向前推动,投资报答开局递减。咱们越是朝着更小的服务行进,老本就会超越好处。在错乱复杂的理想环球中,成功完美的微服务是很艰巨的,更不用说这其实是不用要的。但这并不象征着朝着那个方向行进不会有所裨益。

混合模型

假设不须要不时推动到微服务一侧,那应该在哪里停上去呢?答案是在两边的某个位置,在这个位置有一些掂量可以提高咱们的开发速度和才干,但老本不会超越好处。

我青睐将在两边的某个位置看作是一举两得。是的,咱们可以领有单体(或多个单体),单体周围盘绕着一些微服务。持有这种务虚立场的我能否成了某种异教徒?这种架构的实践好处在于咱们可以将单体的好处与微服务的好处混合起来。单体代码库的便利性和繁难性,加上在必要时可以应用的微服务的灵敏性、可伸缩性和其他好处,使得这种架形成为一个理想的选用。假设有必要,我还可以逐渐从单体拆分出独自的微服务,让某些性能或义务可以从中受益。

混合模型并不是什么新想法,这就是理想环球通常的样子(在两边的某个位置),虽然人们在网络上继续争执不休。

DavidHeinemeierHansson(单体支持者)仿佛很青睐这个想法,他将其称为城堡架构。

大小真的关键吗?

服务越小,就越Micro,作用就越小,咱们就须要越多的服务。随着咱们减小服务的大小并参与服务的数量,艰巨水平也会优化。

或许,咱们应该中止专一于微服务Micro的局部。我以为这会造成人们将自己的服务变得过于小,而这肯定会造成在经常使用微服务时遇到艰巨。

我甚至不确定咱们是如何如此专一于使它们变得尽或许小的。咱们的用意是将软件拆分红不同的局部,分别责任,让每个局部都比全体繁难,从而更容易控制系统的复杂性。但假设服务过于小,咱们或许会被复杂性淹没,无法控制好它们。

虽然每团体仿佛都有自己关于微服务大小的看法,但理想是,微服务的大小没有固定规范。

所以,咱们应该中止争执服务的大小,咱们应该议论的是适宜大小的服务,也就是适宜实践状况的适当的大小——单体或许是频谱较小的一端。咱们的服务,无论大小如何,都应该依据业务和畛域来选择。微服务大小只是后话,全体的组织更为关键。

疑问不在于使服务变得尽或许小,服务小到超越某个水平就会大失所望。它们越小,就肯定与系统的其他局部启动更多的交互才干成功义务。交互越多,咱们就须要付出更高的网络传输老本,更不用说这会使得它们之间的交互变得愈加难以了解。咱们须要在服务大小和服务有多呶呶不休(Chatty)之间取得良好的平衡(感谢Damianlennan提供了"呶呶不休"一词)。

选用对你来说无心义的服务大小,一些服务比其他服务大,这并不是什么疑问。请不要让你的强迫症选择服务的大小——这或许会阻碍一个杰出的架构的产生。将服务变得更大或更小实质上没有对错之分,只需你找到适宜自己的。

不要惧怕扭转你的想法

有时刻,为了了解新技术能否适宜咱们的名目,咱们肯定启动尝试。所以不要惧怕尝试新技术,不要惧怕尝试微服务或混合模型,看看它们能否有效。

尝试之后不要惧怕扭转你的想法,并撤销之前做出的选择。抵赖某些事件不成功并不是件坏事,这是咱们为了取得成功所须要做的事件。尝试不同的事件,启动各种试验,并丢弃那些没有成功的事件。由于微服务在特定名目上不实用并不象征着它们关于其他团队或名目也是蹩脚的选用。

或许更好的是,坚持开明的思想,这是不让自己与新思想和新思想断绝的最佳方式,这些或许是你做好下一个名目所须要的。

加长浏览

BootstrappingMicroservices(

RapidFullstackDevelopment(

检查英文原文


为什么DDD是设计微服务的最佳实践

在本人的前一篇文章《不要把微服务做成小单体》中,现在很多的微服务开发团队在设计和实现微服务的时候觉得只要把原来的单体拆小,就是微服务了。但是这不一定是正确的微服务,可能只是一个拆小的小单体。这篇文章让我们从这个话题继续,先看看为什么拆出来的是小单体。

在微服务架构诞生之前,几乎所有的软件系统都是采用单体架构来构建的,因此大部分软件开发者喜欢的开发路径就是单体架构模式。在这样的背景下,根据经济学和心理学的 路径依赖法则 ,当这些开发者基于新的技术想要把原来的大单体拆分成多个部分时,就必然会习惯性地采用自己最擅长的单体架构来设计每个部分。

在现实中我们经常看到这个法则随处都会发生,微信刚出来的时候很多人说这不就是手机上的QQ吗,朋友圈刚出来的时候他们又会说这不就是抄袭微博吗。很多时候当你兴致冲冲给朋友介绍一个新的东东时,朋友一句话就能让你万念俱灰:这不就是XXX吗?之所以这样,是因为人类在接触到新知识新概念的时候,都会下意识的使用以前知道的概念进行套用,这样的思维方式是人类从小到大学习新事物的时候使用的模式,它已经固化成我们大脑操作系统的一部分了。

理解了这个法则,我们就可以很容易的明白,已经在单体架构下开发了多年的软件工程师,当被要求要使用微服务架构来进行设计和开发的时候,本能的反应方式肯定是:这不就是把原来的单体做小了吗?但是这样做出来的“微服务”真的能够给我们带来微服务架构的那些好处吗?真的能提高一个企业的数字化响应力吗?

不断变化的软件需求和经常被视为效率低下的软件开发一直都是这个行业里最难解决的顽疾,从瀑布到敏捷,都是在尝试找到一个解决这个顽疾的方法,领域驱动设计(Domain Driven Design)也是其中一个药方,而且随着十多年的不断实践,我们发现这个药方有它自己的独特之处,下面我们先来介绍一下这个药方。

领域驱动设计这个概念出现在2003年,那个时候的软件还处在从CS到BS转换的时期,敏捷宣言也才发表2年。但是Eric Evans做为在企业级应用工作多年的技术顾问,敏锐的发现了在软件开发业界内(尤其是企业级应用)开始涌现的一股思潮,他把这股思潮成为领域驱动设计,同时还出版了一本书,在书中分享了自己在设计软件项目时采用的建模方法,并为设计决策者提供了一个框架。

但是从那以后DDD并没有和敏捷一样变得更加流行,如果要问原因,我觉得一方面是这套方法里面有很多的新名词新概念,比如说聚合,限界上下文,值对象等等,要理解这些抽象概念本身就比较困难,所以学习和应用DDD的曲线是非常陡峭的。另一方面,做为当时唯一的“官方教材”《领域驱动设计》,阅读这本书是一个非常痛苦的过程,在内容组织上经常会出现跳跃,所以很多人都是刚读了几页就放下了。

虽然入门门槛有些高,但是对于喜欢智力挑战的软件工程师们来说,这就是一个难度稍为有一点高的玩具,所以在小范围群体内,逐渐有一批人开始能够掌控这个玩具,并且可以用它来指导设计能够控制业务复杂性的软件应用出来了。虽然那时候大部分的软件应用都是单体的,但是使用DDD依然可以设计出来容易维护而且快速响应需求变化的单体应用出来。

到了2013年,随着各种分布式的基础设施逐渐成熟,而SOA架构应用在实践中又不是那么顺利,Martin Fowler和James Lewis把当时出现的一种新型分布式架构风潮总结成 微服务架构 。然后微服务这股风就呼呼的吹了起来,这时候软件工程师们发现一个问题,就是虽然指导微服务架构的应用具有什么特征,但是如何把原来的大单体拆分成微服务是完全不知道怎么做了。然后熟悉DDD方法的工程师发现,由于DDD可以有效的从业务视角对软件系统进行拆解,并且DDD特别契合微服务的一个特征:围绕业务能力构建。所以用DDD拆分出来的微服务是比较合理的而且能够实现高内聚低耦合,这样接着微服务DDD迎来了它的第二春。

下面让我们站在软件工程这个大视角看看DDD究竟是在做什么。

从计算机发明以来,人类用过表达世界变化的词有:电子化,信息化,数字化。这些词里面都有一个“化”字,代表着转变,而这些转变就是人类在逐渐的把原来在物理世界中的一个个概念一个个工作,迁移到虚拟的计算机世界。但是在转变的过程中,由于两个世界的底层逻辑以及底层语言不一致,就必须要有一个翻译和设计的过程。这个翻译过程从软件诞生的第一天起就天然存在,而由于有了这个翻译过程,业务和开发之间才总是想两个对立的阶级一样,觉得对方是难以沟通的。

于是乎有些软件工程界的大牛就开始思考,能不能有一种方式来减轻这个翻译过程呢。然后就发明了面向对象语言,开始尝试让计算机世界有物理世界的对象概念。面向对象还不够,这就有了DDD,DDD定义了一些基本概念,然后尝试让业务和开发都能够理解这些概念名词,然后让领域专家使用这些概念名词来描述业务,而由于使用了规定的概念名词,开发就可以很好的理解领域业务,并能够按照领域业务设计的方式进行软件实现。这就是DDD的初衷:让业务架构绑定系统架构。

后来发现这个方法不仅仅可以做好翻译,还可以帮助业务划分领域边界,可以明确哪个领域是自己的核心价值所在,以后应该重点发展哪个领域。甚至可以作为组织进行战略规划的参考。而能够做到这点,其实背后的原因是物理世界和虚拟世界的融合。

上面介绍了使用DDD可以做到绑定业务架构和系统架构,这种绑定对于微服务来说有什么关系呢。所谓的微服务拆分困难,其实根本原因是不知道边界在什么地方。而使用DDD对业务分析的时候,首先会使用聚合这个概念把关联性强的业务概念划分在一个边界下,并限定聚合和聚合之间只能通过聚合根来访问,这是第一层边界。然后在聚合基础之上根据业务相关性,业务变化频率,组织结构等等约束条件来定义限界上下文,这是第二层边界。有了这两层边界作为约束和限制,微服务的边界也就清晰了,拆分微服务也就不再困难了。

而且基于DDD设计的模型中具有边界的最小原子是聚合,聚合和聚合之间由于只通过聚合根进行关联,所以当需要把一个聚合根从一个限界上下文移动到另外一个限界上下文的时候,非常低的移动成本可以很容易地对微服务进行重构,这样我们就不需要再纠结应不应该这样拆分微服务?拆出的微服务太少了以后要再拆分这样的问题了。

所以,经过理论的严密推理和大量实践项目的验证,ThoughtWorks认为DDD是当前软件工程业界设计微服务的最佳实践。虽然学习和使用DDD的成本有点高,但是如果中国的企业想再软件开发这个能力上从冷兵器时代进入热兵器时代,就应该尝试一下DDD了解一下先进的软件工程方法。

微服务拆分策略和原则

微服务在最近几年大行其道,很多系统的研发都在考虑采用微服务架构,同时,随着 Docker 容器技术和DevOps开发运维一体化等相关技术发展,微服务变得更容易管理,这为微服务架构快速发展创造了有利条件。 在落地微服务的路上,拆分服务是个很热的话题。我们应该按照什么原则将现有的业务进行拆分?是否拆分得越细就越好?接下来一起聊聊服务拆分的策略和原则。

不忘初心方得始终。 在介绍如何拆分之前,我们需要了解下拆分的目的是什么,这样才不会在后续的拆分过程中忘了最初的目的。拆分的本质是 为了将复杂的问题简单化 ,那么我们在单体架构阶段遇到了哪些复杂性问题呢?

首先来回想下当初为什么选用了单体架构,在很多项目刚启动的时候,我们只希望能尽快地将项目搭建起来,方便将产品更早的投放市场进行快速验证。在开发初期,这种架构确实给开发和运维带来了很大的便捷,主要体现在:

但是随着功能越来越多,开发团队的规模越来越大,单体架构的缺陷慢慢体现出来,主要有以下几个方面:

产品初期,应该以单体架构优先。因为面对一个新的领域,对业务的理解很难在开始阶段就比较清晰,往往是经过一段时间之后,才能逐步稳定,如果拆分过早,导致边界拆分不合理或者拆的过细,反而会影响生产力。很多时候,从一个已有的单体架构中逐步划分服务,要比一开始就构建微服务简单得多。同时公司的产品并没有被市场验证过,有可能会失败,所以这个投入的风险也会比较高。另外,在资源受限的情况下,采用微服务架构很多优势无法体现,性能上的劣势反而会比较明显。如下图所示。当业务复杂度达到一定程度后,微服务架构消耗的成本才会体现优势,并不是所有的场景都适合采用微服务架构,服务的划分应逐步进行,持续演进。产品初期,业务复杂度不高的时候,应该尽量采用单体架构。

随着公司的商业模式逐渐得到验证,且产品获得了市场的认可,为了能加快产品的迭代效率快速占领市场,公司开始引进更多的开发同学,这时系统的复杂度会变得越来越高,就出现单体应用和团队规模之间出现矛盾,研发效率不升反降。上图中的交叉点表明,业务已经达到了一定的复杂度,单体应用已经无法满足业务增长的需求,研发效率开始下降,而这时就是需要考虑进行服务拆分的时机点。这个点需要架构师去权衡。当我们清楚了什么时候进行拆分,就可以直接落地了吗?不是的,微服务拆分的落地还要提前准备好配套的基础设施,如:服务接口设计(描述)、注册中心、微服务框架选型、服务监控、服务追踪、服务治理等几大基本组件,以上每个组件缺一不可,每个组件展开又包括很多技术,比如:持续集成、容器技术、持续部署、DevOps 等相关概念,以及人才的储备和观念的变化。 微服务不仅仅是技术的升级,更是开发方式、组织架构、开发观念的转变。

何时进行微服务的拆分,整体总结如下:

1. 单一服务内部功能高内聚低耦合 也就是说每个服务只完成自己职责内的任务,对于不是自己职责的功能交给其它服务来完成。 2. 闭包原则(CCP) 微服务的闭包原则就是当我们需要改变一个微服务的时候,所有依赖都在这个微服务的组件内,不需要修改其他微服务。 3. 服务自治、接口隔离原则 尽量消除对其他服务的强依赖,这样可以降低沟通成本,提升服务稳定性。服务通过标准的接口隔离,隐藏内部实现细节。这使得服务可以独立开发、测试、部署、运行,以服务为单位持续交付。 4. 持续演进原则 在服务拆分的初期,你其实很难确定服务究竟要拆成什么样。从微服务这几个字来看,服务的粒度貌似应该足够小,但是服务多了也会带来问题,服务数量快速增长会带来架构复杂度急剧升高,开发、测试、运维等环节很难快速适应,会导致故障率大幅增加,可用性降低,非必要情况,应逐步划分,持续演进,避免服务数量的爆炸性增长,这等同于灰度发布的效果,先拿出几个不太重要的功能拆分出一个服务做试验,如果出现故障,则可以减少故障的影响范围。 5. 拆分的过程尽量避免影响产品的日常功能迭代 也就是说要一边做产品功能迭代,一边完成服务化拆分。比如优先剥离比较独立的边界服务(如短信服务等),从非核心的服务出发减少拆分对现有业务的影响,也给团队一个练习、试错的机会。同时当两个服务存在依赖关系时优先拆分被依赖的服务。 6. 服务接口的定义要具备可扩展性 服务拆分之后,由于服务是以独立进程的方式部署,所以服务之间通信就不再是进程内部的方法调用而是跨进程的网络通信了。在这种通信模型下服务接口的定义要具备可扩展性,否则在服务变更时会造成意想不到的错误。比如微服务的接口因为升级把之前的三个参数改成了四个,上线后导致调用方大量报错,推荐做法服务接口的参数类型最好是封装类,这样如果增加参数就不必变更接口的签名,而只需要在类中添加字段就可以了。 7. 避免环形依赖与双向依赖 尽量不要有服务之间的环形依赖或双向依赖,原因是存在这种情况说明我们的功能边界没有化分清楚或者有通用的功能没有下沉下来。

8. 阶段性合并 随着你对业务领域理解的逐渐深入或者业务本身逻辑发生了比较大的变化,亦或者之前的拆分没有考虑的很清楚,导致拆分后的服务边界变得越来越混乱,这时就要重新梳理领域边界,不断纠正拆分的合理性。

目前很多传统的单体应用再向微服务架构进行升级改造,如果拆分粒度太细会增加运维复杂度,粒度过大又起不到效果,那么改造过程中如何平衡拆分粒度呢? 弓箭原理

平衡拆分粒度可以从两方面进行权衡,一是业务发展的复杂度,二是团队规模的人数。如上图,它就像弓箭一样,只有当业务复杂度和团队人数足够大的时候,射出的服务拆分粒度这把剑才会飞的更远,发挥出最大的威力。比如说电商的商品服务,当我们把商品从大的单体里拆分出来的时候,就商品服务本身来讲,逻辑并没有足够复杂到 2~3 个人没法维护的地步,这时我们没有必要继续将商品服务拆的更细,但是随着业务的发展,商品的业务逻辑变的越来越复杂,可能同时服务公司的多个平台,此时你会发现商品服务本身面临的问题跟单体架构阶段面临的问题基本一样,这个阶段就需要我们将商品拆成更细粒度的服务,比如:库存服务、价格服务、类目服务、商品基础信息服务等等。虽然业务复杂度已经满足了,如果公司此时没有足够的人力(招聘不及时或员工异动比较多),服务最好也不要拆分,拆分会因为人力的不足导致更多的问题,如研发效率大幅下降(一个开发负责与其不匹配数量的服务)。这里引申另外一个问题,一个微服务究竟需要几个开发维护是比较理性的?

三个火枪手原则 为什么说是三个人分配一个服务是比较理性的?而不是 4 个,也不是 2 个呢?首先,从系统规模来讲,3 个人负责开发一个系统,系统的复杂度刚好达到每个人都能全面理解整个系统,又能够进行分工的粒度;如果是 2 个人开发一个系统,系统的复杂度不够,开发人员可能觉得无法体现自己的技术实力;如果是 4 个甚至更多人开发一个系统,系统复杂度又会无法让开发人员对系统的细节都了解很深。其次,从团队管理来说,3 个人可以形成一个稳定的备份,即使 1 个人休假或者调配到其他系统,剩余 2 个人还可以支撑;如果是 2 个人,抽调 1 个后剩余的 1 个人压力很大;如果是 1 个人,这就是单点了,团队没有备份,某些情况下是很危险的,假如这个人休假了,系统出问题了怎么办?最后,从技术提升的角度来讲,3 个人的技术小组既能够形成有效的讨论,又能够快速达成一致意见;如果是 2 个人,可能会出现互相坚持自己的意见,或者 2 个人经验都不足导致设计缺陷;如果是 1 个人,由于没有人跟他进行技术讨论,很可能陷入思维盲区导致重大问题;如果是 4 个人或者更多,可能有的参与的人员并没有认真参与,只是完成任务而已。“三个火枪手”的原则主要应用于微服务设计和开发阶段,如果微服务经过一段时间发展后已经比较稳定,处于维护期了,无须太多的开发,那么平均 1 个人维护 1 个微服务甚至几个微服务都可以。当然考虑到人员备份问题,每个微服务最好都安排 2 个人维护,每个人都可以维护多个微服务。**综上所诉,拆分粒度不是越细越好,粒度需要符合弓箭原理及三个火枪手原则。**

拆分策略可以按功能和非功能维度进行考虑,功能维度主要是:划分清楚业务的边界,非功能维度主要考虑六点包括:扩展性、复用性、高性能、高可用、安全性、异构性。接下来详细介绍下。 1. 功能维度 功能维度主要是划分清楚业务边界,采用的主要设计方法可以利用 DDD(即领域驱动设计,关于 DDD 的理论知识可以参考网上其它资料),DDD 的战略设计会建立领域模型,可以通过领域模型指导微服务的拆分,主要分四步进行:

以电商的场景为例,交易链路划分的限界上下文如下图左半部分,根据一个限界上下文可以设计一个微服务,拆解出来的微服务如下图右侧部分。

2. 非功能维度 当我们按照功能维度进行拆分后,并不是就万事大吉了,大部分场景下,我们还需要加入其它维度进一步拆分,才能最终解决单体架构带来的问题。

以上几种拆分方式不是多选一,而是可以根据实际情况自由排列组合。 同时拆分不仅仅是架构上的调整,也意味着要在组织结构上做出相应的适应性优化,以确保拆分后的服务由相对独立的团队负责维护。

古希腊哲学家赫拉克利特曾经说过:“人不能两次踏进同一条河流。”随着时间的流逝,任何事物的状态都会发生变化。线上系统同样如此,即使一个系统在不同时刻的状况也绝不会一模一样。现在拆分出来的服务粒度也许合适,但谁能保证这个粒度能够一直正确呢。

1. 不打无准备之仗 开发团队是否具备足够的经验,能否驾驭微服务的技术栈,可能是第一个需要考虑的点。这里并不是要求团队必须具备完善的经验才能启动服务拆分,如果团队中有这方面的专家固然是最好的。如果没有,那可能就需要事先进行充分的技术论证和预演,至少不打无准备之仗。避免哪个简单就先拆哪个,哪个新业务要上了,先起一个服务再说。否则可能在一些分布式常见的问题上会踩坑,比如服务器资源不够、运维困难、服务之间调用混乱、调用重试、超时机制、分布式事务等等。 2.**不断纠正** 我们需要承认我们的认知是有限的,只能基于目前的业务状态和有限的对未来的预测来制定出一个 相对合适的拆分方案 ,而不是所谓的最优方案,任何方案都只能保证在当下提供了相对合适的粒度和划分原则,要时刻做好在未来的末一个时刻会变得不和时宜、需要再次调整的准备。因此随着业务的演进,需要我们重新审视服务的划分是否合理,如服务拆的太细,导致人员效率反而下降,故障的概率也大大增加,则需要重新划分好领域边界。 3. 要做行动派,而不是理论派 在具体怎么拆分上,也不要太纠结于是否合适,不动手怎么知道合不合适呢?如果拆了之后发现真的不合适,在重新调整就好了。你可能会说,重新调整成本比较高。但实际上这个问题的本质是有没有针对服务化架构搭建起一套完成的能力体系,比如服务治理平台、数据迁移工具、数据双写等等,如果有的话,重新调整的成本是不会太高的。

2021年6月11日整理于去往大连的动车上,前方到站:盘锦。

免责声明:本文转载或采集自网络,版权归原作者所有。本网站刊发此文旨在传递更多信息,并不代表本网赞同其观点和对其真实性负责。如涉及版权、内容等问题,请联系本网,我们将在第一时间删除。同时,本网站不对所刊发内容的准确性、真实性、完整性、及时性、原创性等进行保证,请读者仅作参考,并请自行核实相关内容。对于因使用或依赖本文内容所产生的任何直接或间接损失,本网站不承担任何责任。

标签: 微服务

“单体与微服务的技术抉择-拆分还是整合 (单体微服务架构是什么意思)” 的相关文章

谷歌颠覆微服务模型-革命性方法将成本降低99% (谷歌颠覆式创新)

谷歌颠覆微服务模型-革命性方法将成本降低99% (谷歌颠覆式创新)

长期以来,微服务一直被认为是云原生服务应用程序架构的事实标准。2023 年,情况发生了变化,就连亚马逊和谷歌等云巨头都开始革掉微服务的命。 谷歌:微服务走错了 谷歌的工程师们发表了一篇...

微服务容量规划的最佳实践-确保应用程序的高可用性和性能 (微服务需要多少内存)

微服务容量规划的最佳实践-确保应用程序的高可用性和性能 (微服务需要多少内存)

维护众多的服务需要巨大的努力,手动操作已不再可行。以微博的动态推送功能为例,仅远程过程调用(RPC)服务就接近40种。这些服务接口的性能和需求各不相同,一些接口虽然处理请求量大,但响应迅速,称为轻...

微服务全链路灰度颁布施行指南 (微服务全链路追踪)

微服务全链路灰度颁布施行指南 (微服务全链路追踪)

灰度颁布(GrayRelease,也称为灰度颁布或金丝雀颁布)是指在软件或服务颁布环节中,将新版本的性能或服务以较小的比例引入到消费环境中,仅向局部用户或节点提供新性能的一种颁布战略。 在传...

Netflix-微服务设计必看-Eureka-的内部运作机制-深入剖析 (netflix)

Netflix-微服务设计必看-Eureka-的内部运作机制-深入剖析 (netflix)

在微服务架构中,服务发现和注册是确保各个微服务之间通信和协作的核心组件。Netflix Eureka 作为一款开源的服务发现和注册工具,在现代分布式系统中扮演着重要角色。本文将从代码层面深入探...

Netflix-Ribbon-分布式微服务架构的负载均衡神器-深入剖析 (netflix)

Netflix-Ribbon-分布式微服务架构的负载均衡神器-深入剖析 (netflix)

在现代分布式微服务架构中,负载均衡是保证系统高可用、高性能的关键组件之一。Netflix Ribbon 作为 Netflix 开源的负载均衡库,为微服务架构提供了强大的负载均衡能力,极大地促进了微...

别慌!丐版架构图带你秒懂-没用过微服务-轻松面试过关

别慌!丐版架构图带你秒懂-没用过微服务-轻松面试过关

微服务丐版架构图:面试必备 摘要 尽管大模型和云原生备受关注,微服务仍然在软件开发中占有重要地位。本文提供了一张丐版微服务架构图,帮助开发者在面试中了解微服务的基本概念和相关组件。 微服务架构...

稳如泰山!-开发微服务眼花缭乱-掌握这9个最佳实践 (稳如泰山心不乱打一最佳生肖)

稳如泰山!-开发微服务眼花缭乱-掌握这9个最佳实践 (稳如泰山心不乱打一最佳生肖)

微服务最佳实践:构建高效且复杂的生态系统 微服务架构已成为现代软件开发中最流行和先进的架构模式之一。它通过将应用程序分解为独立的、松散耦合的服务,实现了对解决方案的解耦,从而促进了持续交付和开发。...