一次没有WHERE条件的SQL语句引发的OOM问题排查实践!
1、背景
A同学在使用mybatis写SQL语句的时候在某些情况下允许不加where条件就可以执行,结果导致一下子查询出来上百万条数据引发了系统的OOM。
这个案例本身是属于比较简单的那种,不涉及太多其他的技术问题,的确就是纯系统代码自身的问题导致的
2、故障发生现场
我们先来看一下故障发生的现场,某一天突然我们收到反馈说线上一个系统崩溃不可用了,此时当然是立即登录到线上机器去查看日志了,在日志中果然发现了OOM的异常:java.lang.OutOfMemoryError,java heap space。
堆内存溢出了,那我们下一步肯定是把自动导出的内存快照拷贝到自己电脑上,用MAT去分析对应的内存快照了
3、如何巧妙的用MAT工具迅速定位问题代码。
3.1、第一步:检查内存中到底是什么对象太多了
第一步,我们可以用MAT中的一个Histogram功能,去检查一下占用内存最多的对象有哪些
分析内存快照,说白了,无非就是找到占用内存最大的对象,然后就是找到谁在引用这个对象,是哪个线程在引用,接着找到创建这些对象的相关代码和方法,然后你就可以一头扎到对应的源码里去分析问题了。
我们先看下面的图,在这个图里,可以点击下图中红圈处的一个按钮,那个就是Histogram按钮,点击过后就会进入另外一个界面。
接着我们进入Histogram界面,如下图所示:
在这个界面中,其实就可以瞬间看到是谁占用内存过多了,比如这里明显是Demo1$Data这个内部类占用了过多的内存。
这里说了,Demo1 D a