导语
近些年单元化架构在构建多地数据中心,以及如何应对海量请求高并发、低延时的场景中被频繁提及和讨论。单元化架构其实主要解决的是系统扩容、多数据中心容灾、异地访问等方面出现的问题,本文将从单元化概念及优劣势、如何基于TSF建设单元化架构、某国有大行的单元化落地实践三方面进行分享。
作者介绍
崔凯
腾讯高级产品架构师
拥有多年分布式系统研发经验,多年分布式、高并发电子商务系统的研发、系统架构设计经验,擅长主流微服务架构技术平台的落地和实施 目前专注于微服务架构相关中间件的研究推广和最佳实践的沉淀,致力于帮助企业完成数字化转型。
认识单元化
1. 单元化是怎么来的呢?
系统架构在前中期的快速发展阶段,往往更多的是考虑如何快速上线,中台如何支撑更多的系统。但单个机房整体的资源利用率总会存在上限,即使各种技术优化手段再有效,也很难有明显提升,那么单一机房本身就成为了系统瓶颈,瓶颈表现在数据库连接不足、可用区内无法扩容、无法提供异地容灾等情况。
软件系统架构的发展历程中,每一次架构的演进都在解决原有问题,同时带来新的问题。解决系统架构设计问题的有效手段之一是“解耦”,可以简单归结为将“大问题”分解为”小问题”,再将”小问题”分解为更小的问题,直到这个”小问题”可以被我们解决。
单元化架构正是众多优秀架构师将“大问题”分解为“小问题”后实践和思考的结晶。其本质是数据和逻辑的立体拆分,将数据和逻辑划分为相似的“切片”,提高系统对外服务能力的性价比,增加“切片”内链路流转的效率。
可以理解为,单元化垂直切开的是全集的数据和逻辑关系,是AKF立方体中Z轴拆分的一种高级形式。
另外,单元化架构不是凭空出现的,它是分布式架构发展日积月累的产物。也不是所有的业务系统都适合单元化架构,需要系统架构具备一定的技术前提和改造动力,比如微服务化程度、DevOps能力、高可用规划等多方面要求。
2. 单元化,能干啥?
一般情况下,单元化应用场景多是较大规模的分布式系统,尤其是遇到单机房物理限制的情况,快速发展的行业尤其明显,如下简单介绍一些问题场景。
首先,是业务快速发展、流量爆发性增长,给单机房系统带来难以持续扩容的问题。
应用层水平扩容难以有效缓解对于数据层的压力,同时还会造成数据库连接吃紧。
分库分表能暂时缓解数据库压力,但需要封装统一的数据访问代理,同时有一定的代码侵入。如果采用开源数据访问代理,又会有技术组件迁移和维护的问题。另外,开发人员拆的太开反而会增加数据库压力,尤其在秒杀或者双11的高并发场景甚至会引发宕机。
单元化架构通过统一的切分规则,将应用层和数据层进行立体拆分,无论是弹性扩缩容场景,还是多地多中心场景,都可以根据数据中心容量自由划分逻辑“切片”的多少。就好像香蕉树(整个系统)上面的每个香蕉(逻辑切片),可以根据袋子(单元)的大小自由分配和调整,当一个袋子装满了,可以随时将多出的香蕉装到其它袋子中。
其次,跨地域数据中心间服务调用和数据同步时高耗时、低稳定性问题,也是单元化重要的应用场景之一。
比如对于数据一致性比较高的业务,写操作的接入点往往会在某一数据中心A,则当数据中心B有写操作时,数据会通过A数据中心主库写入,再从A将数据复制回B。这种跨地域的调用延时可能在秒级,是很难接受的。
另外,在异地多机房情况下,服务间调用链路可能会在本机房和跨机房中随机选择,这样也提高了调用链路的不稳定性。
单元化架构通过“单元”,将逻辑调用和数据访问在“单元”内形成闭环,只有少数特定场景的调用会跨单元访问,这样几乎大部分的请求在地域内就可以返回,极大程度地减少了访问耗时,避免了跨异地访问链路拥堵造成的服务夯死,提高了链路稳定性。重要的是单元带来的显著的故障隔离效果,链路的可观测性方面也得到了明显改善,即从链路访问层面屏蔽了跨地域访问所带来的上述问题。
最后,基于单元化灵活的流量调配策略,其还可应用于单元级的全链路灰度发布、访问冷热不均场景,此处通过单元级的全链路灰度发布做简单的解释。
常见的方式有两种,分为总控型和自控型。
1. 总控型:一般在流量入口处统一切换流量,单元内应用会在同一时间点准备好新版本并统一发布,适用于如金融、保险等链路上下游强关联、发布版本相对稳定和固定的业务场景。
优点在于管控力度强,故障回滚时产生的损失小;
缺点在于一旦链路中仅个别应用在实际生产发布时故障需回滚(如有BUG),会连带链路中未故障应用也需回滚,打乱未故障应用的版本发布节奏。
2. 自控型:一般由各应用自身负责应用的灰度发布过程,通常适用于服务间松耦合、迭代频繁的业务场景。
优点在于灰度的控制粒度更小、更灵活,不会出现总控型统一回滚的问题;
缺点在于可能需要应用自己保证对外版本的兼容性等。
单元化,没毛病?
1. 成本高
单元化建设意味着现在或未来需要买更多的机器、建更多的机房、搭更多的框架平台做支撑,以及架构升级过程中带来的各种各样的问题,这就需要更多的钱、人、时间。
有“爸爸”的不差钱,不差钱的企业也大概不发愁人才,但时间对每个企业都是公平的,谁都没法获得更多的时间。
2. 改造风险大
单元化改造的参与者众多、落地时间周期长、业务影响面大,比如架构师需要重新做架构设计、研发人员需要针对单元化做适配开发、运维人员需要采购和部署、测试人员需要全量回归所有业务等等,其中某一环出现问题就可能造成延期或者埋下隐患。
所以,单元化改造是一件风险很高的操作,也并不是所有的业务场景都建议单元化改造,需要反复的评估和详细权衡改造的ROI。
3. 运维复杂
单元化建设之前,如果不是特别痛的痛点,运维同学还可以“忍受”。单元化改造后,除了对数据流、控制流的所有层次都增加了路由逻辑,在基础设施(消息队列、缓存、数据库等)方面也增加了很多新的问题,比如跨地域数据同步一致性、应对异地网络尖刺和高延迟等。
这就需要在基础设施的运维可观测性、稳定性、容灾恢复等方面具备较高的水准。另外,保证多地域数据一致性及灾备恢复也极具挑战。
4. 难以理解
单元化改造后,研发人员理解整体架构和业务的难度明显增大了,尤其是系统处于单元化改造过程中时,由于各业务线团队的不同分工和业务上线压力,改造的过程很难保证顺畅的沟通和信息完全同步,很容易在系统边界灰色地带因为理解不一致导致的返工、延期。
再比如,部分遗留系统内部代码混乱、逻辑复杂、没人讲的明白,一般不会主动修改,还有一些访问量很少、极度松耦合的非核心系统,没有单元化的必要,所以整体设计上它们可能不涉及单元化改造,但是对于新加入团队的同学是不了解这里有坑的,那么就可能会存在隐患。
单元化架构设计
1. 如何决策?
架构设计的决策者们对于单元化建设普遍面临进退两难,有的迫于现有的业务压力预期,冒着“边开飞机边换发动机”的风险;有的一直在观望,但由于企业间实际情况不同,自身单元化建设迟迟不能落地,错过最好的改造时机。
可见,决策过程艰难并且会被诸多问题拉扯,比如现有痛点是不是只有单元化才能解决?不通过技术而通过业务变通的手段能否改善?服务和数据的耦合程度是否太高以致难以进行单元化改造?需要准备多长时间作为过渡阶段?整体成本有多大,最终会有哪些有效收益,如何评估收益?
个人理解,单元化改造是个复杂工程,想做到有限时间内精准的评估决策并不容易,而且一旦开始投入就会产生沉没成本。但企业的技术与业务往往是相辅相成,很难说是业务倒逼技术更新迭代,还是技术创新业务发展。
所以,可以尝试跳出仅从技术来分析评估的方式,升维到以企业的视角思考,以当前和未来的技术架构与业务架构持续匹配为目标,可能会让决策者有更清晰明确的结论。
2. 核心要素
单元化设计五个核心要素:
- 单元化规则设计
- 应用代码改造
- 基础设施改造
- 数据存储改造
- 改造落地规划
3. 单元化规则设计
首先,需要确定一个统一的单元化规则中心,用于存储和下发单元化规则。实现方式可以是自身实现单元化规则服务,也可以借助注册配置中心,或者两者共存。
单元化规则启用后很难再进行更改,所以在选择单元化切片的切分维度时要十分慎重。大部分落地的单元化架构使用偏多的是用户ID,比如常见的电商场景,因为通常服务的最终对象都是终端的用户,最需要被“单元”的也是用户的数据。
然而,也有一些强地域场景使用“地域”作为单元化规则的,比如教育类培训机构,中学生校外补课时产生的数据基本都会在本地域内消化,比如报班基本是用户所在地的班级(可能老师就是他在学校里的老师),看课程回放也是在当地复习时看。
强地域类型的还有地图类APP,有些场景会使用设备ID作为单元化路由规则,大部分用户活动的所在地一般不会变,在本地域内产生的数据也会在本地域内被消费。如果有地域迁移的问题,短期内可以通过跨地域访问,长期也可以通过大数据等手段发现后,进行数据迁移。
总的说,单元化规则有两种常见模式:一种通过算法对固定的key运算,比如取模;另一种是自定义,比如多级路由、自定义路由表。也有两种组合使用的情况,比如先进行默认的取模路由规则,如果发现是路由表中的大客户,则路由到指定的数据中心。
4. 应用代码改造
应用作为承载业务的主要载体,需要对接各方要素,在单元化改造中是主要的改造对象。
首先,要对接单元化规则,识别被标记流量,需要开发单元化SDK。在本地缓存单元化规则,并做到实时更新,使得服务或网关可以根据标记快速、正确地流转流量到正确的单元中,当进行单元流量调配时也可及时作出反应。
其次,对接各类基础设施组件,比如负载均衡、消息队列、数据库、缓存等。部分系统由于特殊原因在负载均衡中会涉及一些业务相关的脚本,比如根据UA或业务参数进行页面重定向,此时要一并进行修改。
最后,应用代码改造的主要难点在于改造成本,每个部分的对接都涉及到代码修改,也就意味着要进行开发、测试、发布等全流程。而且单元化改造非一蹴而就,应用代码需要在单元化架构过渡阶段,做好兼容两种架构的代码准备,当出现问题时可及时回滚。另外,也要注意单元化作为架构调整的整体需求就会与业务开发需求相冲突,可能会打乱原有上线计划,给开发人员造成额外的成本和心理负担。
5. 基础设施改造
首先,需要从全局视角思考基础设施改造,比如注册发现中心、配置中心、消息队列、缓存访问代理、数据库访问代理等组件,以实现通过“单元”的维度重新分割服务调用的范围和方式,管理单元级的全局配置和消息消费,数据层根据单元化规则进行的数据切片访问等。
另外,改造还包括支持单元化部署的DevOps、服务治理、任务调度、日志服务、监控告警、资源编排等平台,以实现基于单元的应用版本管理、全链路灰度发布、单元内及跨单元的链路跟踪,单元绑定的鉴权、限流、熔断、路由规则,运维运营方面的单元维度可视化和统计,弹性单元的自动化扩缩容等。
上述场景只是冰山一角,各企业的单元化改造方案因为自身情况的不同而大相径庭,而且涉及众多“准备活动”,比如保证底层网络跨AZ跨region的连通性,底层Iaas资源对自身AZ和region的标记,增加分组标签以形成“单元 虚拟分组”的二层单元结构,Paas平台(负载均衡、MQ、数据库、缓存等)的高可用、数据一致性保障,流量前端的APP添加切流相关的参数或标签,针对单元化对中间件调用的应用代码修改等等。
6. 数据存储改造
数据的单元化方案在改造过程中是重中之重,比如单元化数据库同步方案,一般本地域的数据采用强同步或半同步,异地采用异步同步;数据根据单元化规则拆分、迁移的方案,可在完成分库分表后,配合数据访问代理层、手动禁写、服务路由、限流等服务治理手段,以系统或产品线维度逐步迁移的方式,完成系统的数据单元化操作。
另外,尽量在单元化改造中不要“顺手”进行其它架构改造操作,如微服务拆分、数据冷热拆分等,最好能提前完成。同时并行多想改造会增加实施难度,迁移过程出现问题也难以定位。
7. 改造落地规划
单元化改造是一项整体工程,大部分情况是基于原有架构做改造,大致的改造过程都会经过如下阶段。
架构设计:包括技术可行性评估、应用架构、物理部署架构、业务架构、成本及风险评估等,需要技术团队主要决策人统一通过,为后续改造的整体计划推进提供保障。
改造测试:逻辑理论再完备,还是需要在实际的环境中进行可行性验证。此处可选择在测试环境先进行技术验证,在验证过程中把改造设计时没想到的坑都踩一遍。
并行过渡:测试环境验证完毕后,可先选择边缘系统改造,再选择核心系统改造的顺序(如果是全新系统则直接进行代码开发和系统间对接即可),依次在开发环境->测试环境->预生产环境->生产环境逐步过渡上线,注意代码需同时兼容单元化/非单元化两种架构,以备回滚。
改造完成:在完成所有核心/非核心系统的单元化改造后,体验单元化带来的优势,并等待未来业务的检验。
TSF单元化
1. 微服务平台TSF简介
腾讯微服务平台(Tencent Service Framework,简称TSF)是一个围绕着应用和微服务的PaaS平台,提供应用全生命周期管理、数据化运营、立体化监控和服务治理等功能。TSF拥抱Spring Cloud 、Service Mesh微服务框架,帮助企业客户解决传统集中式架构转型的困难,打造大规模高可用的分布式系统架构,实现业务、产品的快速落地。针对原生Spring Cloud应用与Mesh方式零成本接入。
TSF以腾讯云中间件团队多款成熟的分布式产品为核心基础组件,提供秒级推送的分布式配置服务、链路追踪等高可用稳定性组件。此外,TSF 与腾讯云 API 网关和消息队列打通,帮助企业轻松构建大型分布式系统。
2. TSF的单元化能力
TSF支持使用单元化功能以达到让不同的业务流量根据一定的单元化规则分发到指定的单元里,不同单元之间通过微服务网关实现跨单元调用,当某个单元内的服务器实例出现问题时也不会影响到其他单元业务的使用,使得业务受影响粒度达到最小,同时单元化也为业务容灾高可用提供了强有力的保障。
相关控制台操作流程详见:
https://cloud.tencent.com/document/product/649/55879
TSF微服务网关SDK支持提供基于Zuul、SCG的单元化能力。核心原理为通过TSF命名空间的服务隔离机制,实现单元内闭环、单元外隔离管控的服务发现效果。
SDK配置过程详见:
https://cloud.tencent.com/document/product/649/55877
3. 两地三中心示例
方案说明:
- 基于智能DNS解析实现域名->地域的IDC机房统一,入口通过调整DNS解析规则实现跨地域流量切换。
- 通过入口负载->接入网关,按权重比例配置路由,实现流量切分,同城双活应用互为主备。
- 接入路由到应用,基于网关的标签化路由实现单元服务路由规则匹配。
- 基于本地缓存的单元路由规则进行服务寻址实现单元路由调用。
注意事项:
- 单元内服务调用尽量在单元内闭环,尽量减少跨单元调用。
- 如果业务需要跨单元调用,交由微服务网关管理跨单元请求的转发。
- 业务南北向流量应尽早完成正确单元的路由寻址,出现单元错误时可正常重定向。
- 当出现单元化路由KEY不符合任何单元或访问时不携带KEY时,可报错或按默认单元化规则处理。
- 针对正常/错误的单元化调用流向,做到可监控、可预警、可管理。
4. 调用说明
如上图所示,以银行转账为例,说明TSF单元化三类服务调用顺序。
- 红:代表单元内调用。全部是个人业务数据操作,不涉及与其它单元数据交互,均在本单元内完成闭环
- 黄:同AZ内进行跨单元调用。如DB1中用户向DB2中用户转账,此时服务内置SDK感知到请求需跨单元时,会将请求路由给网关进行二次寻址
- 黑:代表跨网关调用。如DB1中用户向DB3中用户转账,此时对gatewayB来说可理解为一次外部调用
结语
经过对单元化架构相关概念的梳理,可以发现单元化架构是一个即复杂又灵活的架构,复杂在改造需要一定的前提条件,同时要设计合理的单元化规则,谨慎把控整体改造过程;灵活在基于单元化路由可提供的灵活的弹性扩缩及单元级全链路灰度发布,保障业务系统多活容灾的要求。
单元化架构的优势和劣势还有待继续深入研究,在未来助力企业数字化转型不断添砖加瓦。
【参考资料】:
1.https://cloud.tencent.com/developer/article/1823732
2.https://www.infoq.cn/article/how-weibo-do-unit-architecture
往期
推荐
《服务器又崩了?深度解析高可用架构的挑战和实践》
《Kratos技术系列|从Kratos设计看Go微服务工程实践》
《Pulsar技术系列 - 深度解读Pulsar Schema》
《Apache Pulsar事务机制原理解析|Apache Pulsar 技术系列》
欢迎扫码进群交流
扫描下方二维码关注本公众号,
了解更多微服务、消息队列的相关信息!
解锁超多鹅厂周边!
戳原文,查看微服务平台TSF的更多信息!
点个在看你最好看