首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

记一次CPU100%的线上问题处理

问题

昨天刚好是周五,忙碌了一周本以为可以在周五好好轻松下,没成想线上的活动服务出了个问题,市场反馈最近上线的微信活动(是一个类似于测试性格的答题游戏),在游戏结束后结算的时候页面卡死。

排查

我们赶紧查看接口调用日志,发现接口平均响应时间在4s左右。这次活动使用了mongodb,我们之前在做活动的时候碰到过一次忘记给mongo建立索引,导致接口卡死的情况,所以赶紧检查mongo的查询top情况,发现并没有耗时的请求。

这时一个同事提醒我们活动接入了druid,可以检查下是否是sql的问题,我们赶紧打开druid的控制台查看,最慢的sql耗时在800ms,但也不至于把接口拖到4s的地步,不过还是针对索引做了优化。可是情况并没有好转,时间已经过去了十几分钟。

那看来不是存储的问题,那就去找服务器的问题,我们就去看服务器的CPU,内存,网络,发现服务器的CPU达到了100%。

问题总算找到了,本着优先保障线上使用的目标,在问题得不到很快定位的情况下,我们决定再弹出一台服务器,替换掉目前线上有问题的服务器,这样也可以保护问题现场,帮助我们排查问题。

这个时候我们从线上dump出线程dump,但是从中并没有发现什么有用的信息。

新的服务器挂到SLB上之后,我们观察了下,它的CPU很快也达到了100%,这时我们也还没有找到问题出在哪里,由于之前的服务器已经没有流量进来了,我们尝试着重启了这台服务器,然后访问这个活动,观察日志的输出,发现开始的时候一切都是正常的,但是最后的结算接口调用后CPU直接达到了100%,那就是说程序中出现了死循环,导致线程卡死了得不到释放。

问题知道之后我们就去看这个接口的逻辑,发现 是一个while循环,然后里面一个很复杂的逻辑,在询问了对应开发人员这段逻辑之后,我们在不能很快定位原因的情况,写了一段简单的替换逻辑,虽然不能完整的实现原先的逻辑,但是用户使用上并没有太大的区别。

解决

重新上线后,重新试了下流程, 没有再出现CPU100%的问题了,至此问题解决。

总结

在晚上的例会上我们分析了原因,是代码提交之后没有完整的code review流程,导致代码没有检查就提交测试,而有些bug在测试环节是很难发现的。

经验

关于问题排查

线上问题检查基本流程是

CPU,内存,网络

数据库索引(包括nosql)

日志

线程dump,堆dump分析

关于代码编写

针对本次bug是因为while循环没有正常退出导致的,所以业务中应该尽量避免使用while循环,尤其是业务复杂的时候,可能考虑不全,不能保证循环一定能够退出。这个时候应该使用可预见的有限for循环+if退出条件来代替while循环(web引用几乎没可能有需要无限循环的业务)。

其实代码在一开始就进行code review,可能就能够避免很多潜在的问题,而且尽量不要写一些太复杂的业务逻辑,如果真的很复杂,极有可能是这个实现方式就不正确,可以考虑下有没有替换方案。

  • 发表于:
  • 原文链接http://kuaibao.qq.com/s/20180331G0UN4C00?refer=cp_1026
  • 腾讯「腾讯云开发者社区」是腾讯内容开放平台帐号(企鹅号)传播渠道之一,根据《腾讯内容开放平台服务协议》转载发布内容。
  • 如有侵权,请联系 cloudcommunity@tencent.com 删除。

扫码

添加站长 进交流群

领取专属 10元无门槛券

私享最新 技术干货

扫码加入开发者社群
领券