249建站之家:亿级APP支付宝在移动端的高可用技术实践
高可用在移动端的重新定义
高可用原本属于服务端的概念,阿里巴巴的服务端都在讲高可用。服务端的高可用重点讲的是停机时间短、服务不可用时间短。
移动端的高可用从服务端借鉴过来之后进行了重新定义,因为客户端不存在停机时间概念。
所以,移动端高可用的定义是指通过专门的设计,结合整套技术体系,保证用户所遇到的技术不可用总次数很低。
移动端高可用的目标
简单来说,移动端高可用的目标就是实现可用率达到 99.99%,这里的可用率是支付宝自己定义的概念,指的就是用户在使用 APP 的时候,可用次数在使用次数当中的占比,可用率达到 99.99%。
也就意味着用户使用 1 万次支付宝中的 9999 次都必须是可用的,最多只有一次不可用。为了实现这一目标,还会将任务拆解成为不同的子目标分别攻克。
移动端高可用的核心打法
目标的实现还是比较困难的,因为让可用率达到 99.99% 是一个很高的指标。而为了能够努力实现这个目标,支付宝也自创了一套核心打法。
主要分为以下四个部分:
客户端可用性监控。用户遇到不可用的时候,要把造成不可用的问题收集并上报上来,并且要提供足够的诊断信息用于分析解决。
高灵敏监控报警平台。需要实现当线上的问题刚刚出现苗头的时候就立即能够发现。
快速修复能力。当发现问题之后不仅要保证能够修复,还要保证修复的速度足够快。对一些级别高的故障,支付宝要求在一个小时之内完成快速修复。
故障演练。
支付宝在移动端高可用技术实践
如上图所示,是支付宝实现的移动端高可用技术架构图,大家可以看到支付宝移动端高可用的技术架构设计也是围绕上述的四个核心打法展开的。
客户端可用性监控
问题采集
客户端可用性监控的第一步就是问题采集,当 APP 发生不可用时必须能够感知和采集到问题,这是基础的基础,如果没有这个基础后续什么都不能实现。
怎样确保当用户出现了不可用情况时能够采集到问题?这是比较困难的,因为我们不能保证一定可以采集到所有类型的不可用问题,但是还是会通过多种方法尽量地实现全面覆盖。
支付宝把不可用问题分为稳定性不可用和业务不可用两个方面。对于稳定性不可用而言,通过 2.0 阶段的逐渐摸索以及各种反馈渠道、问题搜集渠道的补充,现在已经可以把各种各样稳定性的不可用问题搜集得比较全了。
比如传统的闪退、卡死等以及不容易被监控的黑屏、白屏以及非闪退类型的异常退出等。
目前已经采集到了大部分的问题,当然可能还会存在遗漏,对于这些遗漏的问题,还需要通过不停地搜集并补充到这个体系中。
对于业务不可用而言,在开发时会对于业务不可用问题进行埋点,只需要将业务不可用埋点纳入到系统里面来,就能够基本覆盖最重要的业务不可用问题。
统一管控
当问题采集上来之后,需要通过统一管控形成客户端可用率指标。通过这个指标可以全面地评估线上某一个人群中的可用情况,而不需要像以前那样逐一检查各个指标并在最后给一个不太准确的评估结果。通过统一管控可以设计出整体的监控和报警机制以及各种算法模型,并且其扩展性更好。
埋点上报
埋点上报这一功能是非常核心的,因为后续还要利用不可用埋点做高灵敏,所以埋点的实时性、准确性、到达率的要求特别高。
并且对于不可用埋点而言,当客户端已经发生了不可用时才需要进行上报,而在这个时候客户端情况很可能非常恶劣,甚至此时客户端可能已经无法启动了,即便是这样也要保证埋点能够上报。
为了实现这一点,我们利用了一些小技巧,比如对于 Android 系统而言,支付宝通过独立的轻量级进程来单独上报埋点,即便主进程已经挂掉了,但是埋点也能够实时上报上来。
对于 iOS 系统而言,采取在线上 hold 住进程使其报完埋点再退出去的方式,并且后续还有补偿机制,即使出现遗漏埋点的情况也能够使其最终能够上报上来。
通过问题采集、统一管控和埋点上报,基本上可以保障当用户遇到不可用问题时可以收集问题并上报服务端,做好了第一步的基础。
高灵敏度系统模型
在问题收集到的情况下需要用高灵敏系统模型做监控和报警。监控和报警在 2.0 时代就已经存在了,比如当大盘上监控的闪退率出现异常情况时就会进行报警。
但是高灵敏系统模型要做的是在线上问题刚刚出现苗头的时候就可以发现,而不是等到大盘出现波动才发现。
所以这个模型的关键在于分析决策的过程中,它会基于用户的人群特征、问题特征把线上采集到的不可用问题进行聚合再进行分析,通过预制的一些算法模型和规则来判断是否产生了异常,如果最终判断的确有异常产生了则会输出一个异常事件。
举个例子,比如线上的某个业务发布了一个新的 H5 离线包版本,其中某一个页面的卡死率很高。那么使用这个页面的用户就会形成一个特征人群,这个特征人群的页面卡死率就有异常的波动,这个时候就会输出异常事件。
但是此时大盘并没有太大波动,因为特征人群的人数并不多,但是后台可以捕获到异常事件。
当异常事件输出之后,可以通过附带信息准确地匹配到相应的负责人以及开发、测试人员,告警系统会告知负责人进行处理,并且会根据问题的严重程度采取不同的告警方式,可能会采取邮件、钉钉或者电话等方式进行告警。
在问题非常严重的情况下,如果几分钟之内没有响应就有人打电话给负责人了。通过这样的告警机制就可以保证无论什么时间,只要线上出现异常问题就可以迅速地感知到。
高可用容灾平台
通过上述的内容,我们已经可以实现对于可用性问题的感知了。接下来分享如何通过高可用容灾平台修复异常问题。
这里通过整体的故障容灾过程进行分享,如下图所示,当一个故障进来了,会向相应的负责人发出告警,这时负责人需要检查这个故障是怎样产生的,到底是由于线上变更导致的,还是由于客户端本身的 Bug 导致的。
如果是因为线上变更导致的则比较好办,因为现在的系统比较灵敏,只要故障刚一发生,在短时间内负责人员就可以收到告警。
之后就可以到发布记录中检查这段时间内发生了哪几次变更,可以很快地基本了解是哪一次变更导致的故障,并采取相应的处理策略。
如果可以回滚就进行回滚操作,不能回滚就需要进行紧急发布,如果不能紧急发布就要依赖客户端进行修复。
比较麻烦的是和变更没有关系的情况,此时就需要通过异常携带的诊断信息或者通过获取一些日志来检查问题为什么产生,问题的产生有时候是因为兼容性问题。
比如某个厂商灰度发布了一批和支付宝兼容性不太好的系统,导致出现了各种各样的问题,这种情况下就要通过动态修复解决。
也可能一些客户本地出现了严重错误,比如说产生了一些脏数据,或者安装时因为市场的临时性 Bug 导致了大量安装失败,最终导致支付宝打不开。
对于这种情况而言,可以通过本地容灾做一些恢复工作,进而实现客户端的自动恢复。
总之,通过上述的过程,可以使故障得到解决。从下图中可以看出,支付宝在高可用容灾中致力于两点:
希望每个故障都有一个对应的方法能够实现修复。
希望流程尽量清晰并且顺滑,希望不要在流程上浪费太多时间,并且将故障尽快地解决掉。
高可用的动态修复体系
移动端高可用和服务端高可用的重大区别就是移动端的发布比较困难,所以需要依靠动态修复技术。
动态修复并不是新的概念,像 hotpatch 等技术都已经非常成熟了,目前也有很多可选的动态修复方案。
但是,虽然在高可用的动态修复体系中,hotpatch 属于比较重要的点,但是并不是最主要的点,因为它也存在一定的局限性,也有不适合的时候。目前,支付宝基于多种修复手段搭建了高可用的动态修复体系。
支付宝的高可用动态修复体系主要由以下三部分构成:
修复手段
修复手段有很多种,并且有轻有重。轻的手段在线上进行一些配置就可以解决线上不可用的问题,重的手段可以把整个模块完全重新部署下去。具体应该选择哪一种修复手段应该根据故障的情况来看,选择效率最高、风险最低的修复方式。
下发通道
这一点与埋点上报的要求有一点类似,也需要高实时性和高可靠性。当用户已经不可用了,常规方法拉不到线上的修复方案的时候,能够解决的办法再多也是没有用的,所以需要保障无论面对多么恶劣的情况下都能够把修复方案拉下来。
下发通道的实现方式有很多种,最终实现只要能够联网一定可以将修复方案拉下来,如果暂时不能联网,那么一定要在联网之后将修复方案拉下来。
发布平台
设计动态修复的发布平台的时候非常关注的一点就是把修复方案推送给真正需要它的用户,也就是把修复方案推给已经出现或者可能出现这个问题的用户。
这样做的原因是每一次的动态修复其实也是一次线上变更,本身也是存在风险的,如果对于所有用户都进行推送则需要比较长的时间进行灰度来保证安全,但是如果能够只对目标的小众人群、特征人群推送方案,这样灰度时间会很短,修复时间也会很短。
支付宝在客户端请求修复方案的时候,会根据客户端的人群特征、是否发生过这个问题以及有没有发生这个问题的可能来判断是否把这个修复方案推送给他们,这样可以很快地完成推送过程。这在图中称之为“智能修复”,其实称之为“定向修复”更为准确一些。
高可用实战经验
在这里和大家分享支付宝在高可用实战中的两个案例,其中一个处理的比较成功,另外一个则不是很成功。
案例 1:一个业务运营推送了一个错误的菜单配置,而客户端没有做好保护。在运营推送配置的 10 分钟之内,相关的负责人都收到了报警,并且很快地查到是这个配置导致的。
之后运营将马上对于配置进行了回滚,这个过程所影响用户数比较少,所以是一个比较成功的案例。
这也是支付宝最期望的运维过程,实现了及时发现、很快修复并且影响用户数很少。
案例 2:在一次大促的时候,一个业务开启了限流,客户端弹出一个限流的页面,这个页面有 Bug,会导致黑屏,进而导致用户无法进行操作。
但是由于当时的可用性监控不完善,所以这个问题没有被监控到,最后是因为用户的反馈才知道出现了问题,到问题出现的第三天,反馈量已经积累到一个明显的程度了,才发现这个问题。
之后,我们迅速地对于这个问题进行了分析和解决,最后定位到限流的问题,一个小时之内确定了问题所在,并暂时把限流先关掉,后来把这个 Bug 修复掉了之后再将限流打开,这样客户端才恢复正常。
虽然最终把问题完善地解决了,但是这一过程存在非常明显的缺陷。首先是发现的太晚了,这是因为可用性问题没有覆盖到。
另外,因为没有足够的信息使得决策的过程比较慢,花了 1 个小时进行分析才能够止血,直到现在我们也不知道这三天到底影响了多少用户,但是这一事件肯定对支付宝的可用性造成了不小的伤害。
而现在,支付宝实现了移动端的高可用,以后像这样的事情不会再发生了,当出现故障时,支付宝可以在第一天很短的时间内就可以搞定问题。
故障演练
有这样一句话“避免故障最好的方式就是不断演练故障”,所以我们要通过可控的成本在线上真实地模拟一些故障,进行故障演练,检验高可用体系是否可靠,同时也让相应的同学对系统、工具和流程更加熟悉,当真正发生问题的时候可以快速地处理。
为了更好的检验这套东西,支付宝采用了攻防对抗演练的方式,成立了一个虚拟小组,他们会想办法模拟线上可能出现的故障情况,而另外一组人则利用移动端高可用技术接招,把对方研发的问题快速地处理掉。
这样做好准备以后,当真正出现故障需要进行处理的时候,我们也已经能够熟练地应对了。
在前进中探索
最后再谈一下对客户端可用性运维未来的思考:
智能化
前面提到了高灵敏的模型,大家可以看到在决策的过程中往往需要依赖预设的算法模型、规则以及数值等,这些都源于常年积攒下来的经验。
但是这也存在一些缺点:一是有可能出现误报;二是为了防止误报太多,这个模型不敢做的太紧,所以模型的灵敏度属于比较灵敏,而不是极度灵敏。
我们期待通过智能化的方式,通过人工智能、机器学习的方法实现决策过程的智能化,可以做得更加灵敏,将问题发现的时间再提升一节,而且这目前已经不仅仅是一个想法了,在支付宝的很多场景中已经开始使用智能报警了,我们也在调研和尝试接入这个东西。
自动化
这部分主要指的是容灾过程的自动化。我们想把前面展示的容灾过程做的很顺滑,但是其中很多步骤都需要人来做,这样时间成本、决策成本会很高。
所以我们希望把尽量多的步骤转成自动化方式,至少是半自动化的方式,这样才能让容灾过程更加顺滑,使得修复时间产生本质的飞越。
产品化
我们希望当客户端可用性更加成熟之后赋能给其他类似的 APP,通过这个过程积攒更多的经验,发现更多的问题。并且在未来合适的时间,或者 3.0 版本的客户端可用性不能满足需求的时候再去建设 4.0 可用性运维体系。
推荐
-
-
QQ空间
-
新浪微博
-
人人网
-
豆瓣
