如何在金融企业推进故障演练?中国人寿分阶段实践总结

2023-12-04 12:08:54 浏览数 (2)

作者介绍

中国人寿研发中心高级工程师——刘玢

TakinTalks社区专家团成员。拥有多年开发和运维经验,专注高可用领域,目前负责中国人寿混沌工程等多项高可用举措的规划和落地实施,对于构建高可用系统具有深入的理解和实践经验。

温馨提醒:本文约4600字,预计花费9分钟阅读。

背景

在最近六七年时间里,中国人寿对原来烟囱式的架构做了持续改造。对诸如长险、短险、万能险等等独立系统中的类似功能,做了横向的专业化拆分、微服务拆分。新架构在带来效率提升的同时,也带来了更多不确定性风险,如微服务数量的指数级增长、架构越来越复杂、问题定位难度加大等等。

从2022年安全事件及生产风险原因分析看,中国人寿安全事件及生产风险主要包括非版本类变更引发、第三方或硬件故障、版本或历史缺陷、生产长事务或者海量数据引发等,其中非版本类变更引发、第三方或硬件故障两项总和超过50%。

一方面,微服务增多导致版本翻倍增长,带来了更多的变更风险;另一方面,“1min-10min-30min”的故障处理要求也是不小的挑战。总体上,因为缺乏抓手导致我们对性能、安全、兼容性、可维护性等多方面都缺乏质量信心。

基于此,中国人寿高可用工程规划了一系列稳保能力,并于2022年开始落地基于混沌工程的故障演练。囿于金融行业生产环境的特殊性,目前中国人寿已率先完成了在故障演练在测试环境和准生产环境的落地。

今天我将主要围绕中国人寿故障演练的项目背景、目标思路、技术方案等,分享其在预知故障和降低不确定性风险方面的实践成效。

一、故障演练想要达成哪些目标?

1.1 故障演练目标

故障演练的目标主要分为两块,业务目标和技术目标。通过基于混沌工程平台的故障演练能力建设和演练实施,从开发、测试、运维、灾备各个领域帮助各系统发现和解决潜在问题,提高系统稳定性和可用性,增强团队协作能力和故障排除能力。

1.1.1 业务目标

事前(从架构设计角度):增强业务可用性,预防事故发生;

事中(从系统运维角度):提高故障发现能力和告警能力;

事后(从故障处置角度):提升应急处置时效,降低故障影响范围和时长。

1.1.2 技术目标

开发领域:去除架构设计单点,验证系统容错能力;

测试领域:生产故障回归测试,极限场景测试;

运维领域:验证监控发现能力和告警有效性,验证应急预案有效性,缩短故障处置时间;

灾备领域:验证灾备切换预案的适用性和有效性。

1.2 落地思路

第一个是安全优先。先从测试环境演练入手,再慢慢过渡到生产环境,稳定安全优先。

第二个是分步实施。先做一些简单的场景,然后再做复杂的场景,稳步推进。同时,先引入开源工具,再加强自主掌控,不断提升故障演练系统支撑能力。

第三个是加强协同。故障演练和做容量规划、灰度、在线压测等都有很大的不同,大多数时候业务团队会认为故障演练将破坏其系统程序而抵触不配合。因此,协同沟通以及混沌理念宣传非常重要。

二、技术方案如何选择?

2.1 平台功能规划

技术选型是整个项目落地最重要的一块。我们将功能规划分成了五部分,实验配置、实验管理、安全管控、监控整合、故障注入。前面两部分各家都大同小异,这里将重点分享后面三个功能规划背景。

1)安全管控

这部分规划我们花费了最多的精力和时间。在做混沌工程时,大家首先都会关注如何建立系统稳态,如何控制爆炸半径等,而金融行业系统的安全管控尤为重要,所以我们花了大量时间,与诸如阿里等一线公司做交流和调研,借鉴成功的经验。具体实现过程我将在后面展开。

2)监控整合

我们要把原有的监控能力做整合,来适应混沌平台的需求。中国人寿做过很多监控能力的建设,如机房监控、主机监控、网络监控、数据库监控、服务链路监控等等,原来的监控平台对这些监控能力都做了接入,但为了告警方便和防止误报,很多监控数据都做了抽样,比如按分钟做一个统计数据再整合起来。如果直接给混沌平台来使用,会导致时效性不足或者故障被掩盖。因此,我们需要重新做监控能力的整合。

3)故障注入

故障注入能力可能是大多数人关注的重点。我们规划的故障注入能力包括基础故障(如CPU资源、网络资源、磁盘、进程、内存)、JVM类故障、网络请求类故障、消息中间件故障、K8S引擎故障、Cattle引擎故障等等。这部分我们花了较长时间做收集整理。

此外,我们还做了一些定制开发的故障。因为仅基于开源工具,很多场景故障无法模拟。举个例子,中国人寿现在使用了大量的中间件,一个Java工程使用很多外部jar包,有些外部包又依赖其他包,整个生态非常庞大,而外部的故障工具只能对其中某些地方做故障注入,不能完全满足实际的故障模拟需求。所以需要很多定制化的故障开发来补齐这部分能力。

2.2 技术选型过程

完成功能规划后,我们从业界主流的混沌工程平台中挑选了一些产品进行深入研究和试验测评。从故障注入能力、安全管控能力、实验配置与编排、界面易用性、部署难度、服务支持、扩展性兼容性等7个方面,做了深入的分析和对比。

基于技术自主可控的思考,最终我们选择了“自研 开源”的方式。基于开源的ChaosBlade,进一步做了定制化开发,包括自定义故障的开发、监控能力整合等,形成了现有的混沌工程平台。

三、如何分阶段落地故障演练?

整个故障演练工作可以分成三个阶段。目前已经完成测试环境和准生产环境的故障演练,我将重点分享这两个阶段的落地实操。

3.1 故障演练-测试环境

3.3.1 整体工作成效

从2022年7月开始至今,总计完成13个系统测试环境的故障演练,累计进行30轮演练,发现143个风险点并采取预防措施,整改问题超过50个。

3.3.2 演练过程

1)第一轮:线上分散式演练

第一轮演练是线上分散式的,持续时间一周以上。主要参与人员有混沌教练、产品架构师、测试人员。其中,产品团队需要提供架构文档(如物理架构、逻辑架构、技术栈情况等)、历史故障清单(如上下游关系比较近的系统故障)、演练的重要关注点等。

在此过程中,我们会根据系统技术栈和系统架构,先在故障演练库中选出适合的基础故障,再根据实际沟通情况补充应用适合的故障。接下来,基于开发环境对挑选出来的故障做预演练,其目的就是通过合适的方式生成故障——有些故障比较简单,通过故障工具可以直接生成,但需要找到合适的位置并做深度剖析;还有一些故障需要定制开发,并做演练迭代。

整个过程根据系统的复杂度,短则持续1周,长则2-3周。演练完成后,就能形成适合该系统的比较完整的故障清单。

2)第二轮:集中研讨整改措施

以线下集中的形式开展,时间是半天左右。将混沌教练、产品经理以及产品组架构师等等骨干全部召集,对第一轮确定的故障清单做集中演示。同时,现场讨论并确定整改举措。有些故障会涉及多个角色,也有可能产品组不认可问题整改意见,此时则需要多轮讨论,最终商定具体的整改方案。

3)第三轮:应急预案有效性验证

此阶段加入运维部署负责人,还是以线下的形式进行,主要对应急预案的有效性进行验证,时间也是半天左右。

此轮我们会挑选一部分和运维紧密相关的故障,对第二轮整改后的系统进行可触发应急处置的故障演练。运维人员介入并根据应急预案实施一遍,看看是否能覆盖并及时处理故障。同时,也会在现场讨论应急预案的举措是否合理、是否需要增加、是否需要完善等等,并可能在现场做多次迭代实验。

3.3.3 演练结果

对于金融系统来说,真正敢上生产环境做演练的几乎没有,所以我们在测试环境的演练收获会相对少很多。前面讲到我们总计完成了13个系统测试环境的故障演练,其演练结果和问题大致可做如下分类。

从数据中可以看出,大部分问题集中在监控缺失和告警规则。尽管监控平台已经建立了好几年,但是从演练结果来看,监控告警能力并不如大家想象的乐观——存在监控盲区或者需要达到一定阈值才会在监控中呈现、告警规则不合理等等。这里也是我们测试环境演练最有价值的收获之一。

(中国人寿某系统演练问题清单)

3.2 故障演练 - 准生产环境

3.3.1 演练背景

客户活动管理系统是中国人寿的客户节活动平台,在活动高峰时,瞬时TPS可达到8000以上。为应对即将到来的客户节活动,我们在此系统上做了准生产环境的故障演练。之所以称之为准生产环境,是因为虽然它本身是生产环境,但在客户节来临前,它没有生产流量,所以我们可以直接在生产环境做尺度更大的故障注入。

3.3.2 演练过程

演练需同时依赖在线压测平台和监控平台进行。由于是在生产环境演练,所以必须用在线压测的方法才能把生产流量打上去。另外更重要的一点是,虽然客户活动平台刚上线没有生产流量,但是其上下游系统也会有生产风险,所以需要依靠在线压测平台做流量区分,将测试流量打入影子库中。同时,一些不能调用的接口也需依托在线压测平台做Mock。所以,先有在线压测平台后,再来建设混沌平台,工作推进会更加合理。

3.3.3 演练成效

1)依托在线压测平台全面验证各个模块容量;一般情况下,容量验证依靠性能测试。但性能测试有个比较大的难点,即A模块产生性能瓶颈但下游的B模块还未到达瓶颈,此时需要性能测试不停做生产变更和配置调整才能达到最优。而通过混沌工程平台,简单对CPU或内存做一定比例的占用、对网络延时做少量调整即可检测出链路上各个模块的性能极限。

2)对数据库高可用、PAAS平台多活、应用限流熔断、监控和告警等进行了全面验证;

3)首次生产应急演预案有效性验证,应用弹性扩容、数据库扩容和重启等。

四、故障演练解决了哪些实际问题?

4.1 开发领域

1)强弱依赖梳理

  • 重保期间人力成本降低。开门红是每家保险公司都非常重视的活动。由于业务量巨大,在这种活动重保期间,我们以前的做法是所有关联系统的运维人员、产品经理都需要24小时值班做支撑,这样的成本投入是非常高的。而依托故障演练的强弱依赖梳理,可以精确知道哪些系统更重要需要24小时保障,而其他不关键的系统则可以适当降低响应要求。了解组件之间精确的依赖关系,能够更合理安排运维支持,更大程度上减少人力成本。

2)高可用举措有效性验证

  • 架构设计的落地情况验证。以前有很多架构设计,经过评审上线后落地好坏是很难评估的,比如在架构设计文档里承诺实现的点,实际上线后可能由于各种原因并未达到设计要求,混沌工程故障演练能有一定检验效果。
  • 单点故障容错验证。主要验证集群中一个单点产生故障后,业务是否还能继续。在实操中,业务压力较大时,其中一个节点故障,整个集群的可用性并不一定如设计的那样有效。比如,在一次对某系统生产故障复现的故障演练中,当我们对Redis做故障注入,发现当主节点瞬时内存大量占用出现故障时,从节点并未切换为主节点。所以单点故障的容错验证是有必要的。
  • 限流、熔断阈值验证。如前面提到,有些设计看起来是没问题的,但是不经过验证,它真的不一定是可靠的。
  • PaaS、网格等多活验证。中国人寿有自己的PaaS平台,做了一套多云多活的高可用设计,包括一套信创云做补充。通过混沌平台我们验证了PaaS平台和网格的多活策略的有效性。
  • 中间件高可用验证。对Redis、消息队列等依赖比较重的系统特别需要这一块的实验。

4.2 测试领域

1)生产故障回归测试

  • 月度生产故障根因分析支持。在生产环境出故障或者难以还原现场时,我们会用混沌工程模拟现场。尽管分析出来的根因可能会不一样,但这对周边系统的高可用提升具有借鉴意义,即当生产发生此故障时,周边系统的高可用手段应该如何发挥作用。
  • 重大生产问题复盘支持。

2) 极限场景模拟测试

  • 性能测试无法模拟的场景支持。有很多场景是无法通过性能测试模拟出来的,比如发压的压力达不到、或者流量配比不科学、或者中间一些环节的容量不够,无法把足够的压力传导到指定模块上,此时可以通过混沌工具占用一部分的CPU或者内存,再去做极限场景的性能测试。

4.3 运维领域

1)监控发现能力和告警有效性验证

监控发现能力补全和告警有效性验证。前面讲到进行了30轮演练后,我们发现监控缺失和告警规则不合理占大部分。我相信这种情况应该在各家公司是普遍存在的。

2)应急预案有效性验证

  • 促进应急预案的完善;
  • 锻炼运维队伍,提升故障处置时效。

五、未来展望

未来我们希望打造更便捷,更安全,更智能的故障演练服务。

更便捷:当前在做故障演练时,我们的投入是很大的,基本是把混沌小组最厉害的工程师、混沌教练,还有各个产品团队的架构技术骨干都集中到一起才能把整个工作开展起来。难度高、专业性强导致了便捷性的不足。未来在更便捷方面,我们想像使用自来水一样做故障演练。

更安全:当前我们还没有真正上生产。一是因为大家信心不足,二是监控指标的有效性、完整性以及依托监控指标快速恢复现场的能力也还有待进步。

更智能:我们也在思考人工智能和混沌工程的结合,比如说不需要人工再做复杂的架构和技术栈分析、历史故障分析,甚至实现自动的故障注入和实施等。(全文完)

Q&A

1、混沌教练需要具备什么样的素质?

2、混沌工程构建故障是用的哪些测试工具?测试环境和准生产环境使用的工具有哪些不同?

3、故障演练、在线压测如何分工与协作?

4、怎么做到月度生产故障和重大生产问题故障的混沌场景,镜像生产数据?

0 人点赞