一次真实的线上OOM问题定位
尊重原创: 王政 依码平川 原文链接
概述
近日,负责的一系统生产环境上出现了OutOfMemoryError,伴随着这个问题随之而来的是一堆Full GC, CPU 百分之百,频繁宕机重启等问题,严重影响业务的推广及使用,此类问题一般处理起来比较棘手,本文将此问题的出现及定位解决过程做下梳理,以便对后续处理类似问题提供参考指导。 注:该问题前面发了一版,因有些描述不太恰当,后来删除了,少数先得者看到了,想再看下发现已被删除,私信咨询我怎么找不到了,由此可见,很多同事还是比较在意此类问题的,很好,重新梳理下,补上一篇。
问题出现
软件:WildFly standalone 8.1.0.Final(OpenJDK)
报警内容:日志中有OutOfMemoryError信息
环境:PRD
报警级别:严重
报警时间:2019-04-09 11:04:59
当前时间:2019-04-09 11:06:03
监控项名称:jboss日志OutOfMemoryError
最新数据:2019-04-09 11:03:38,791 ERROR [stderr] (RMI RenewClean-[net.sf.ehcache.distribution.ConfigurableRMIClientSocketFactory@1d4c0])Exception in thread "RMI RenewClean-[net.sf.ehcache.distribution.ConfigurableRMIClientSocketFactory@1d4c0]"java.lang.OutOfMemoryError: Java heap space
第一步:重启服务
做好机器隔离,重启服务,保证不影响业务使用!
第二步:收集dump文件
第三步:利用JVM故障处理工具分析问题
打开jvisualvm工具
载入dump文件
查找保留大小最大的对象
重点关注前几位
查看实例数最大的实例
分析可能的原因
从实例上看JDBC42ResultSet占用空间最大,从而大胆猜测与查询相关,那么就看详情中能否找到是哪个sql导致的问题,查看owningstatemeng语句集:
查看原始sql:originalSql
sql详情:
纳尼,where 1=1?相当于没带条件查所有记录,那么,表中有多少记录呢,不多,也就20万不到吧
至此,改问题的原因似乎显而易见。
第四步:紧急发布
于当晚拉紧急版本,通宵发布处理,以免问题重现。
总结
此问题是由于研发人员疏漏,查询字典表数据未带查询条件,导致查出表中所有记录进行ORM处理导致内存溢出。定位过程看似简单,但如何能在第一时间迅速排查原因并给出解决方案,难度还是不小的,由于缺乏经验,往往不知该怎么入手,况且线上异常场景复杂多变,不保证这个地方优化了,后续就没有问题了,需要在现网环境经住考验才行。
事实证明,此问题优化后,现网仍然有较多其他问题待解决,目前正在组织专家会诊,待后续有时间再做总结吧。
来源: https://mp.weixin.qq.com/s?__biz=MzU2Mzg3NDUyNA==&mid=2247483847&idx=1&sn=eb224addb210bc19d751a9ac29aeb4b4&key=6d5f3fc8a79580fa0633b94c19075fd1245f16d6cc5c666b1ef66c505ed3ab197464c72826f0e3b438ff5e6121d87d94672f1e91df029aa1d2f0000b023122af5e7361645adf86f8c7664eb4b924c8b5&ascene=1&uin=MTQ1Mzg2MTQ0MA%3D%3D&devicetype=Windows+7&version=62060526&lang=zh_CN&pass_ticket=nJLRjgUVd7gz1eGbWZP5FBRfD39lvgkIgmQUs4ng9Rrd0kUvJezxXXlu7io2Pf4L&winzoom=1