美文网首页
一次排查OOM的总结

一次排查OOM的总结

作者: fooboo | 来源:发表于2019-05-08 23:04 被阅读0次

    昨天项目的某个版本线上出现宕机,非其他原因引起的coredump而是OOM,系统内存不够了选择kill某个占用内存最高的进程,而我们的业务进程在宕机那一刻的快照显示占用25GB多内存,总内存才32GB。

    我对OOM这块不是很熟悉,后来查了一些资料,看了下/var/log/message下面的信息,再结合业务进程中的日志,宕机那会的操作看起来没什么问题。据同事反馈说运营那边说是有几百万的元宝进行购买(土豪啊),就这么多信息。可能是在测试,然后日志中邮件的记录比较多,一万多条但也不是很多。

    因为邮件系统实现不是我做的,之前的版本线上从来没有出现过这样的问题,可能是某些操作造成压力过大偶现的,但也是坑。该系统对每个玩家的邮件数有个上限,超过进行删除,后来我就仔细分析日志,发现对某些邮件删除多次,是滚动行的,比如第一次删除有一次,第二次删除两次,逻辑不对,另外的同事在本地测试时,发现删除是正常的,可能压力不够大。

    这时候我联想到之前排查的问题,我大概知道原因了,在下班前,看了下邮件系统的实现(虽然实现是有一定的问题),发现在发一封邮件时,会生成一个全局邮件id,在这之前会判断玩家的邮件数是否达到配置中的上限,此时进行一次DB拉去该玩家的全部邮件数据(不知道为什么要这么设计),然后依次判断是否有超时的,此时可能再操作DB进行删除。这么看,正常流程貌似没有问题,但因为内部服务间是call异步请求,协程去处理,当压力过大时,对同一个玩家生成很多邮件的时候,可能造成把请求透传到DB那边造成压力,之后发现都没有删除等逻辑错误。

    大概问题是找到了但不确定为什么会造成内存极具下降到被kill,因为看代码其他地方也没有对数据做缓存,哪怕一次请求两万条邮件(出问题是该玩家有一万八百多),预估下整个数据量大概在十几兆的样子(预估)。

    后来就把这个问题反馈给负责该模块的同事,继续排查,然后把线上数据库拉下来在本地复现。看日志,可能出问题那会,系统对邮件功能进行大量操作(当玩家背包满后,发的奖励这些都是走邮件),导致有很多的请求要处理,本应串行化的操作就如那种查缓存,查不到就去DB,造成多次处理,然而还占用内存(这里直接相同操作查DB)。后来把进程拉起后,大半夜又出现OOM还是宕在相同的日志内容处,即操作邮件的时候,所以基本可以确定是邮件的问题。后来怎么改,其实这个是设计原因,出个临时解决方案,后期重新实现邮件系统。

    像这种偶现的问题,在本地无法测试出,只有极端情况才会出现。之前也帮着排查到三四个类似的问题都记录在之前的文章中。上一次是关服时导致玩家数据不一致情况。

    这边定时存储玩家数据,而设计的时候有两份数据,导致关服的时候,有份数据没有保存到。那边实现的时候,每一分钟保存多少条数据,但是数据量太多,有十几万条,然后关服的时候就大概等了多少时间就退出。但是这里并没有把数据都落地完就退出了,这段时间并不能把事情都做完,导致只做了一半,造成严重的问题。当然这个问题也因数据量多少而出现问题。

    定位和分析问题的能力,包括解决问题的能力,有的时候需要经历线上问题去分析和复线。在本地测试通过的功能,很可能表面上没有问题,但夹杂着其他操作结就会出现不一样的情况,严重的时候会很严重。但是还是要冷静下来,尽量总结下问题,并看下相关代码,是不是偶现的,有些偶现的问题,需要好好分析代码,比如在什么情况下会出现问题,有没有测试没有覆盖到的情况等。

    希望代码少bug。

    相关文章

      网友评论

          本文标题:一次排查OOM的总结

          本文链接:https://www.haomeiwen.com/subject/dupboqtx.html