云布道师
如何建设全面的高可用及容灾架构体系,是一个涉及到广泛领域的话题,将分成上、下两篇呈现给读者。本文将在上篇的架构基础上,构建完整的故障与危机的处理能力,同时通过持续运营与组织保障机制的协同,打造出全面的高可用及容灾架构体系。如何构建故障与危机的处理能力
故障的隔离与逃逸:打造处理重大故障的容灾体系
在面临大规模系统故障的时候,能否有能力把故障隔离在一定范围内,限制故障的影响,并且有能力把业务流量从故障区域内迁移走,将会对业务的连续性产生决定性的影响。
1、故障隔离能力
故障隔离的例子在我们身边比比皆是,比如现代电力设施中的断路器(旧设施中用保险丝)可以隔离电路故障,保护基本电路、避免连接部件受损。再比如船舱里防漏水的隔板,会把船舱隔成若干个空间,这样可以在船舱漏水时限制漏水范围,避免整个船舱都进水。还有早期以太网使用 CSMA/CD 和网络分段技术,将网络分隔成多个冲突域,减少碰撞形成更快的整体网络等等。下面我们就来看看故障隔离在高可用及容灾领域中是如何发挥作用的。故障隔离与可用性和可扩展性的关系
通常一个业务系统会由一系列的服务组成,服务之间相互关联和依赖。在处理业务请求时,当一个服务调用另外一个服务,然后挂起等待同步响应时,就创建了一个串行同步链,这个同步链上涉及的服务越多,由某个服务故障导致全面故障的概率就越高,这就是所谓的“系列故障的乘法效应”,这时候可以通过提高基础服务的可用性和冗余度来减少风险,更关键的是需要通过分解故障域,来进一步隔离故障,限制故障所产生的影响。假设我们基于客户维度划分了故障域,一个故障域内的系统只服务于一组客户,这样当一个故障域内的系统出现故障时,就会立即知道发生了什么事情,而且影响只限于该故障域内系统服务的那组客户。故障隔离使事件更容易被检测、确认和解决,除了可以防止事件在系统中蔓延,也可以使事故的解决过程更聚焦,整体上减少服务恢复的时间。随着业务的发展,系统的代码行数、服务器数量以及系统整体的复杂度都会快速的增长,要处理这种复杂度的增长,就需要将代码隔离成面向服务或者面向资源的系统架构,让不同的团队负责不同的服务,每个团队将成为这个服务领域内的专家,由此而产生的专业化将充许更快的新功能开发、更快的解决已知或现有的故障和问题。因为错误修复、问题解决和新功能的开发更快,整体的研发效率也会得到提升。进行故障隔离的三大原则
1)故障域之间的 shared-nothing 架构故障域之间绝不共享,这个原则在一些领域可能是非常困难的,比如边界网关的路由器,但追求 shared-nothing 是我们进行故障隔离设计的出发点,越彻底应用这个原则,结果会越好。我们需要 URI/URL 域的分组开始,隔离而且使用专门接入层集群、负载均衡、应用服务器、数据库和存储。如果两个服务使用了相同的存储,那么就只相当于在应用层形成两个较小的故障隔离区,当应用服务器出现失败时,这样的隔离会起作用,但当存储失败时,两个故障域就会同时都失败。同步通讯是指任务业务请求必须等待响应完成,如果故障域之间采用了同步通信,那么一个服务的阻塞就可能会对其也的服务产生意想不到的效果,那么就会使事故的影响跨越了故障域,结果使整体服务的可用性下降。相应的如何故障域之间必须要有通讯,那么可以采用异步的方式,服务不需要等待请求的响应,只是向服务发出一个消息,告诉它你希望有一个响应,这样就不会影响和阻塞其它的请求。根据前两个原则,我们从可用性和效率上来看,需要将一个业务请求在尽量在单个故障域内完成处理,尽量避免跨故障域的通讯和交互,达到故障隔离的最好效果和服务间交互效率的最大化。如何实施故障隔离: 通过多重分解来隔离故障
理解了上面关于故障隔离与可用性和可扩展性的关系,以及进行故障隔离的一些基本原则之后,那么下面来说一下我们该如何进行故障隔离的设计。在上篇构建韧性的应用基础架构章节中,架构可扩展部分我们提出过对系统 3 个维度的拆解,这个实际上也就天然对应了我们通过多重分解来建立不同故障隔离域的目标。首先,要确保把和业务关系最紧密的服务和可能失败及有需求限制的服务与其它服务做适当的隔离。比如电商业务最核心的可能就是交易流程,包括从导购、下单到支付的全部流程。那么最好的方式就是将交易流程涉及的核心服务进行适当的故障隔离。另外,针对像大促秒杀这类对资源需求有热点的场景,也需要考虑做故障隔离机制的建设,避免热点给系统带来的稳定性风险。如果系统中某些服务多次引发故障,就需要考虑针对这部分服务或组件建立起相应的故障隔离机制。可以利用故障复盘会议,关注那些反复造成可用性问题的相关事件,也应该隔离这部分防止对系统稳定性产生持续影响。对于跨越多个服务的复杂业务场景,它会依赖我们在上篇 2.1 章节中所描述的 Z 轴扩展模型,对可扩展性有着较高要求的系统往往都要寻求沿 Z 轴的分割,沿着客户的边界(用户 ID)进行实施。先在架构的存储和数据库层完成(数据分片),接着创建一条从业务请求到数据存储的完整业务处理单元作为故障隔离域。这种多重服务可以从共享中获得较高的成本效益,因为它可以把整个业务场景中的多个服务划为单一的故障域。需要注意的是,如果这个业务场景中某个或某几个服务压力格外高,需要考虑是否进行单独的故障域划分。2、故障逃逸能力
在完成了正确的故障隔离域划分后,需要建设的就是如何将业务流量从某个故障域中进行分流调度,完成故障逃逸的能力。透明多级分流
在进行业务流量如何调度的说明前,我们先梳理一下用户在使用系统的过程中,一个业务请求会走过什么样的处理路径。首先,通常会从浏览器发业务请求,通过域名服务器解析找到系统的入口 ip 地址,经过网关、负载均衡器、缓存、业务服务集群等一系列设施,最后到达末端存储于数据库服务器中的信息,然后逐级返回到用户的浏览器端。这其中要经过很多不同的设施和技术组件。- 位于客户端和网络边缘的设备,能够最快速的响应用户请求,减轻给后方的 I/O 与 CPU 压力(
- 能够线性拓展处理能力的部件,便于伸缩并可以使用较小的代价水平增加机器来获得与处理业务量相匹配的并发性能,应尽量作为业务逻辑的主要载体(
- 有全局性影响的技术部分,这些部件的稳定性影响较大,需要时刻保持着容错备份,维护高可用性状态(
- 单点部件,通常只能依靠垂直扩容,如升级机器本身的网络、存储和运算性能来提升处理能力,如位于系统入口的路由、网关或者负载均衡器(原则上这些也都可以做集群,但一次网络请求中通常避免不了至少有一个是单点的部件
当对系统进行流量规划时,在充分理解这些部件的价值差异的同时,可以遵循下面一些通用的设计原则:
- 减少单点,如果某些单点是无可避免的,则应尽最大限度减少到达单点部件的流量。在系统中往往会有多个部件能够处理、响应用户请求,比如要获取静态图片资源,浏览器缓存、内容分发网络、反向代理、Web 服务器、文件服务器、数据库都可能提供这张图片。引导请求分流至最合适的组件中,避免绝大多数流量汇集到单点部件(如数据库),同时依然能够在绝大多数时候保证处理结果的准确性,使单点系统在出现故障时自动而迅速地实施补救措施,这便是系统架构中多级分流的意义。
- 奥卡姆剃刀原则,在对多级分流的手段有全面的理解与充分的准备的同时,还需要清晰地意识到这些设施并不是越多越好。不是每一个系统都要对高并发、高可用有着极高的要求,需要根据需求,以及用户量、峰值流量和团队本身的技术与运维能力来考虑如何部署这些设施才是合理的做法,在能满足需求的前提下,最简单的系统就是最好的系统。
通过客户端缓存、域名服务器、传输链路、内容分发网络、负载均衡器、服务端缓存这些与功能无关的技术部件节所构建的多级透明分流的体系,可以获得高可用、高并发的架构收益和价值。
业务流量类型
我们可以用流量的亲和性和状态属性来对业务流量进行类型分析,根据不同的流量类型在容灾场景中设计不同的故障逃逸策略。无状态流量,绝大多数 web 访问流量是无状态的,由用户从网络边缘设备向一个或多个数据中心发出的网络请求组成。无状态流量可以通过将其从故障数据中心或特定的集群、机架或机器组中重新路由来调度走。粘性的交互服务,通过将请求固定到特定服务器来改善用户体验,由这些服务器维护会话中用户的状态。可以通过重新路由传入的会话请求并拆除已建立的会话以迫使它们重新连接到其他机器,来进行粘性服务流量的调度。复制流量,在灾难场景中我们可能需要改变甚至阻止复制流量进出分布式存储系统的故障数据中心。可以在其他数据中心中重新创建副本以提供读取。这需要更改影响资源共享的一些配置,比如数据链路同步方向。有状态的流量,对于基于主从复制的系统,主节点故障的解决措施是将辅助设备提升为新的主设备。这可能需要将状态数据从故障数据中心复制到新数据中心。状态数据需要根据网络容量进行仔细控制,以便将数据传输到健康的机器。业务流量迁移
在业务流量调度的过程中,会涉及到不同数据中心(业务单元)间流量比例的调整,路由规则的变更,部分服务的启停,业务配置数据的变更等不同的任务之间的协同工作,这就需要我们建立一个整体的业务流量调度框架来统一协调工作,这里面需要关注下面的一些点:
- 任务间的依赖:需要梳理清楚并使用 DAG 图等方式对任务间的依赖关系进行管理。
- 任务执行条件:理清任务执行的前后置条件,通常前置条件是用来检查服务的健康状态,后置条件是用来判断流量调度进度。
我们可以面向服务构建起不同的切流方案脚本,通过依赖关系将不同的流量调度任务进行聚合,协同完成业务服务流量调度,并可以对切流方案进行进行演练和评估,让我们能够提前排除业务流量调度过程中会碰到各种风险。
当我们发布一个新服务时,可以利用场景驱动的方式来分析在不同类型的故障和灾难场景下与上下游服务的依赖关系。此外,我们还可以利用跟踪系统分析目标服务如何通过 RPC 和网络通信与其他服务交互,结合服务发现系统将交互映射到特定的服务。再进一步分析服务的跟踪日志,以基于服务行为的因果模型来推理基于状态的依赖关系。确定了两个服务的流量之间的依赖关系,也就可以决定切流的顺序。
针对相互独立的服务我们可以采用并行的方式进行流量迁移。对于一个新服务,我们可以通过一些高可用工具来检测与周边服务的强弱依赖关系,并使用小规模的切流来谨慎地验证指定的依赖关系,同时密切监视所有相关服务的健康状况。通过逐渐扩大切流测试的半径,直到所有级别的切流都可以常态化进行。以一种以可控、可扩展的方式来验证依赖关系。
在每次切流测试以及每次容灾演练之后需要进行关键路径分析,通过识别容灾切流依赖关系图中的瓶颈,帮助我们优化恢复时间。我们需要检查对缓慢、繁重任务的依赖性,并尝试将这些依赖性移出关键路径。如果依赖项延长了关键路径,那么需要评估依赖项是否是业务上的关键强依赖服务,并考虑其故障恢复成本。针对不影响系统正确性的弱依赖项,可以降级的方式来加快恢复的速度,我们通过分析关键路径上的依赖性来筛选弱依赖项。我们还可以通过故障演练,以受控的方式有意打破弱依赖关系,以评估相应的服务级别影响。
在业务流量迁移过程中会涉及一些共享资源(例如,服务器计算能力和网络带宽),在进行流量迁移的过程中需要确保共享资源不会过载并减少资源争用的影响,需要遵循以下三个原则:
我们通过定期测试验证共享基础设施有足够的容量来承载由于流量迁移造成的利用率峰值。通过对网络的全面监控和控制,观察到引流如何影响峰值网络利用率。当测试过程中出现瓶颈时,就需要调整路由策略、流量比率和优先级安排方案或带宽预留配置,以便我们能够安全地调度服务流量。
为了处理共享资源无法支持需求的大范围故障事件,我们需要制定了一个流量迁移的优先级方案。要优先考虑尽快迁移面向用户服务的流量,以限制用户可感知的故障影响,然后排出有状态的服务流量。这确保了对最终用户的影响最小化,同时也最小化了状态迁移的开销。
最后,我们需要准备系统在资源过载的情况下优雅降级方案。通过使用使用预案开关来关闭某些弱依赖服务或者降低服务请求的复杂性(例如,通过逐步关闭算法复杂性以降低服务器计算能力)。
在进行流量迁移时要通过健康监测,实现闭环反馈,以安全地调整切流的速度。切流的速度由步长(流量迁移的比例)和下一步前的等待时间决定。当进行流量迁移时,需要根据底层系统的健康状况调整相关的参数进行切流速度的调整。
步调机制要力求平衡安全性和效率,尽可能快地完成流量迁移而又不让其他数据中心过载。就是将切流操作分解为多个步骤,并对每个步骤调整权重,以确保流量变化不会违反任何数据中心的健康指标。切流应该采取多个步骤(其间有指定的等待时间),逐渐增加流量转移比例,以便允许系统在负载平稳增加的情况下进行预热而不会过载。需要关注可以覆盖其服务健康状况的几个关键指标,通过切流测试来实验不同的启动速度。基于从速度到健康指标影响的经验映射,在不损害健康或安全的情况下将默认值调整为最大速度。3、基础设施容灾能力
当我们谈到基础设施层,就包括了像硬件设备、网络、IDC 等,它是所有系统正常运行的基础,这里面的容灾及高可用保障机制会涉及众多专业的细分领域,比如:网卡的 bond 模式、硬盘 RAID、交换机双上联、多线 BGP 接入、从市电到服务器的全双路供电、IDC 的冗余柴发等等。我们可以利用云计算的能力和优势,把上述众多专业领域的容灾能力建设屏蔽在云计算的 IaaS 层,减少业务应用容灾能力建设的复杂度,充分释放云计算的红利,那么云计算是如何进行基础设施层能力的封装的,下面以阿里云为例进行一下简单的说明:首先,做为阿里云整个体系架构最底层的是磐久基础设施层,它可以把百万台服务当成一台超级服务器或者超级计算机来进行管理,接下来在底层的硬件服务器之上插入 CIPU,底层的服务器资源就从硬件的服务器资源变成了云化的服务器资源,并进一步的可以被跑在上面的飞天云操作系统进行统一的调度。然后,飞天云操作系统中又包含了三层的横向的服务类别,最底层是内核级的平台服务,再就是系统级别的服务和原生级别的服务。其中内核级平台是支撑飞天云操作系统和阿里云的底座,也是阿里云能够作为云上新基础设施的底层技术支撑。内核级平台就包含了神龙计算平台、盘古存储平台、洛神网络平台和安全内核对应的防护能力。接下来是系统级别的服务,也就包含了 IaaS 这一层服务,即弹性计算、存储和网络服务,同时也包括了对外的安全服务。系统级别的服务和内核服务,是有一一的对应关系的。这也反映出了内核平台层的服务,主要是为了支撑系统级别服务的。当一个云上的客户去用阿里云的时候,必然是要使用到系统级别服务的,也就是计算、存储和网络服务。当有了计算、存储、网络。在其上可以构建或支撑更多的客户侧业务应用,也可以充分享受到云化的基础设施带来的强大的稳定性保障能力。 全生命周期的稳定性保障:SRE 运维实践
SRE 是业界管理大型复杂服务的最佳实践,与 SRE 有些相近的概念是 DevOps,DevOps 的核心思想是将 IT 相关技术与产品设计和开发过程结合起来,减少人工操作强调自动化,以及利用软件工程手段执行运维任务等,这些思想和 SRE 相近,但 SRE 更聚焦于业务的性能和可用性方面,用软件工程的方法解决高可用方面的问题,同时沉淀了一套高可用保障方面的组织结构、管理结构和流程制度方面的最佳实践经验沉淀。为了提高服务的可靠性,SRE 重点要关注服务的以下几方面内容:通过系统设计早期 SRE 的引入,会使得服务开发能够更加关注“面向失败设计”,这样可以让该服务的可靠性得到提升。但随着对 SRE 专业知识需求的持续增长,就需要 SRE 的能力能沉淀出基于最佳生产实践的服务框架,将一些架构模式和代码模型进行标准化,封装在框架体系内,通过构建框架模块来实现这些关注重点的标准解决方案。而这也是构建统一 SRE 运维平台的基础。在这种模式下, 通过 SRE 和 SRE 平台来承担大部分础设施服务的软件开发和维护的职责,特别是限流降级、系统保护、自动化、流量管理、日志和监控等服务,而研发团队就可以更专注于业务逻辑的开发。
持续运营与组织保障机制的建立
如何应对高速业务技术发展带来的架构不确性
随着业务的发展,系统的架构也是在不断快速变化和演进过程中的,包括软件应用系统和硬件基础设施,那么在这个不断演进的过程中,就会引入大量的变化和潜在的风险,那么我们就需要通过常态化的测试和演练,来验证我们的系统是否在整体上还处于一个稳定的状态,而没有随业务和系统的发展而出现架构劣化的趋势。1、容灾演练
我们的容灾架构和预案要求始终与我们快速发展的软件系统和物理基础设施保持同步,然而,由于大规模系统的复杂性和动态性,使得维护系统的最新信息(例如,服务依赖性)是很具有挑战性的。所以我们就需要利用容灾演练来持续验证和建立对容灾架构和预案有效性的信心。容灾演练可以通过有计划的测试,将模拟发生故障的数据中心的面向用户的流量和内部服务流量进行切流恢复。内部服务除了业务系统内部交互外,还需要包括异步作业、离线数据处理通道、机器学习系统、应用交付系统以及许多其他基础设施关键组成服务。我们需要每周或每月有计划地运行多次容灾演练,以在最近测试最少的数据中心上模拟各种类型的灾难场景。测试安排在一天的不同时间进行,以涵盖各种流量场景(例如高峰和非高峰时间)。另外,还需要有计划地安排每次演练的持续时间,以了解灾难发生时,我们整个基础设施中其它的服务组件的工作是否符合预期。运行容灾演练可以带来的收益:- 验证相应的容灾预案能够有效缓解和恢复各种类型的灾难,并满足我们的恢复目标;
- 通过确定各种灾害情景下的能力需求来进行容灾预案规划;
- 测试在不会使切流目的站点过载的情况下,能够达到的最大切流速度;
- 通容灾演练,在切流过程中利用共享资源来识别资源瓶颈;
- 通过演练来梳理隐藏的复杂系统间依赖关系,不断发现新的依赖关系。
容灾演练的预期目标是不会对用户造成任何可见或服务级别的影响。如果这一预期没有得到满足,我们就需要与系统研发团队一起跟进,以了解为什么给定的灾难场景没有得到很好的处理,并安排后续演练来验证修复。
2、故障演练
这部分内容在上篇 2.2.3 章节有过说明,这里不再赘述。 非技术的关键因素:组织保障机制建设
组织保障机制的建设在整体个业务连续性体系建设中起着非常重要的协同作用,限于篇幅在本文中不会做详细展开讨论,只对重点部分稍做框架性的描述。1、预案机制
凡事豫则立,不豫则废,我们只有建立起完备的预案机制,才能在故障或灾难发生时从容有序应对。预案机制的关键就是如何能够让预案能够有效管理和高效运转,那么最核心的就是如何将预案进行结构化,并且能够与业务容灾和故障处理过程动态地关联起来。另外,在预案管理能力的建设过程中,需要关注点还有:2、制度流程
故障应急流程
稳定性管理制度
3、组织建设
业务连续性建设的锚点:
广义的容灾架构体系的建立
全面的云上业务连续性建设,由于涉及面广、建设难度大,不容易找到一个好的建设方案切入点,而容灾架构体系由于其自身的重要性和领域的聚焦性,恰好形成了一个比较好的建设锚点。在广义的容灾架构体系语境下,会涉及架构、能力、运营、组织等几个方面的内容,通过打造稳定性基础架构,构建故障与危机处理能力,形成持续运营与组织保障机制来建立起大容灾架构体系,夯实云上业务连续性建设的基础。具体各个方面的建设内容和方式,上文都有所提及,下面我们再来做个系统化的总结梳理。 架构
高可用技术架构
应用架构
能力
故障逃逸能力
基础设施能力及规范度
运营
故障及应急处理流程演练
组织
制度流程
组织建设
演进,云化可持续架构质量管理模型
容灾架构体系是云上业务连续性的基石,也是在推运用户进行云化及可持续性架构演进过程中技术架构层面撬动能力最强的解决方案,可以带动一系列的产品和服务输出,也可以给用户带来能力的成长、机制的建立和效率的提升。那么,如果我们把架构视角拉升到云化可持续架构建设这个层面,我们在架构特性、架构能力、持续运营和组织保障这几个方面就需要关注更多的关键点,例如:在架构特性层面,我们需要从应用架构、数据架构和IT基础架构几个维度全面展开,在架构能力方面,除了业务连续性保能力,还需要关注服务敏捷交付能力、复杂性治理能力、成本优化能力、数字资产沉淀与创新能力等等。
通过云化可持续架构质量管理模型,可以使我们拥有云化可持续架构的建设规范和度量标准,把主观评判变为客观标准,更好的指导和帮助用户建设云化架构基础,沉淀企业 IT 技术能力,持续技术运营带来业务创新和收益增长。但限于篇幅,这部分内容不在本文中展开论述。后面,架构质量管理模型会在星轨、CMH 中落地,尝试在评估体系、模型驱动架构设计等领域形成可赋能的工具化能力。星轨 / 工具中心:面向交付标准化、运维自动化场景,通过开放的工具市场,生态赋能认证,提升工具的透传和复用性,为各角色实施人员提供生产力工具,降低人工操作门槛。
云迁移中心(CMH):阿里云自主研发的一站式迁移平台。为广泛用户的迁移上云项目提供自动与智能的系统调研、云上规划、迁移管理,简化和加速用户上云过程,辅助用户业务化可视化管理迁移全生命周期。
CMH 企业版:是一款辅助客户云上架构迭代的工具,其通过内置的配置管理数据库 CMDB,多源感知系统,巡检系统,事件体系,流程管理体系。帮助客户完成当前架构感知,从架构组成和架构结果标准度量架构,并持续跟进架构演进。
后记,持续走下去的勇气
由于本文题目涉及领域较广,所以虽一再精简,但仍然会行文较长,并且其中涉及的很多知识点不能详细展开,会比较浅薄。在文章中论述的内容也难免会有诸多谬误和纰漏,还请大家批评和指正,文中涉及引用的一些思想方法出处的文章书籍列在附录中供大家参考,如有遗漏还请见谅。架构理论源于生产实践的沉淀,只有通过不断的项目经验积累才能滋养更深厚的架构理论,欢迎奋战在相关领域的小伙伴,有技术、项目上的想法和经验一起交流,相互促进,在高可用及容灾、云化可持续架构这个领域一起探索。附录:参考资料
- https://www.aliyun.com/product/apds
https://developer.aliyun.com/ebook/7696
应用高可用服务 AHAS:
https://www.aliyun.com/product/ahas
《某银行系统云原生上云最佳实践》
《阿里容灾硬骨头--中心容灾战役设计策略与方案》
《The Are Of Scalability》
《凤凰架构:构建可靠的大型分布式系统》
《混沌工程:Netflix 系统稳定性之道》
《SRE:谷歌运维解密》
《Building Evolutionary Architectures》
- 《Mitigating Datacenter-level Disasters by Draining Interdependent Traffic Safely and Efficiently》
团队面向北京、上海、杭州等地持续招聘,更多接触外部各行业数字化转型的机会,广阔天地,大有作为,详情请见:https://talent.alibaba.com/off-campus/position-detail?lang=zh&positionId=926514