
























香港业务方计划在4月初做消费券活动,预计在4月有一波大促流量并且远超去年双12的流量水位,因此对香港业务方的核心链路重新做一次新流量水位的压测,保障当前集群能满足预期的流量水位需求。
经过两次实验性压测后,通过公式计算出新流量水位预计下上下游每个应用预计的集群大小和入口流量大小,并对各个上下游应用执行机房扩容和入口流量限流阈值调整。
万事俱备后,3月15日晚开始执行压测,按梯度逐渐将入口流量提升到45%时整个集群的资源使用情况十分稳定符合预期,但当流量水位从45%调整到55%时突然大量报错请求返回失败,因此中断压测排查问题。
查看报错日志后,发现错误原因为DB连接池耗尽。压测的核心链路理论上应该全部使用缓存,于是去查看压测期间对应的监控记录,如下图,发现问题:
应用入口流量增长后对远端缓存的读取量同比增长符合预期,但DB查询量却突然暴增13倍,第一反应是缓存击穿导致大量DB查询请求,然后致使数据库慢查询而耗尽DB连接池,最终导致当前的问题。



于是剩下的就只剩验证了,首先故障应用没有使用本地缓存,因此集群所有机器对每一个数据都共用一份远端缓存,一旦远端缓存过期失效,则瞬间集群所有集群读取不到缓存后会同时请求DB查询数据,符合DB查询增长的监控情况。
然后挑了一个单机节点查询故障时刻的DB查询日志,发现几乎全是对同一条记录的查询操作,也符合缓存击穿的猜想。
确定了是因为远端缓存失效而导致的缓存击穿问题,后续的解决就很简单了。实际上这个问题去年压测的时候就已经暴露过,但由于去年水位远低于本次的水位,因此实际上去年在监控上看也仅仅是压测期间偶尔会出现DB调用次数的尖刺和DB耗时尖刺,无实际影响,所以一直把这个缓存击穿问题的优化方案给搁置了。
根本原因是应用使用的缓存均为远端缓存,无本地缓存。压测期间当远端缓存一旦过期,会导致瞬间大量DB查询请求,然后DB出现慢查询后耗尽数据库连接池,造成大量请求失败的问题。
因此需要对缓存做治理,防止出现远端缓存失效后,瞬时DB查询暴增的问题:
改造后缓存读取流程如下图:

以上方案虽然解决了缓存过期后的击穿问题,但没有解决数据未预热场景下,突然流量导致的击穿问题。因此未来还需要实现预热能力,通过定时任务对数据库中可能为热点数据的记录做预热,提前加载到远端缓存中,防止突发流量击穿。
此内容由惯性聚合(RSS阅读器)自动聚合整理,仅供阅读参考。 原文来自 — 版权归原作者所有。