由于是金融公司,所以不便透露代码和系统名称。

背景描述

1) A系统的UAT环境会推送数据到B系统。


wKiom1cuKVmAGXWVAAAEfSfIr6A654.png


2)由于系统间没有采用消息中间件进行解耦,B系统的连接池出现泄露导致A系统功能也受到影响。

3)生产环境没有出现问题。

4)服务器为IBM外包管理,无权查看JVM的DUMP,无权登录到服务器机器。

5)连接池并非马上全部泄露,而是渐渐的被吃掉。


采用技术框架:

    SEAM+SPRING+HIBERNATE

    数据库ORACLE RAC



诊断:

由于生产环境并没有发现问题,大概率可以断定是由于数据问题导致。从DBE团队提供的一份数据来看,几乎所有的连接SESSION都是执行了某一个同样的SQL(Hibernate生成)后,卡死。


1)追踪到SQL,从SQL追踪到Hibernate,然后找到了相应的代码。(运气较好,此段SQL只出现在了我们一处代码上面,很容易就锁定了泄露嫌疑区域)


wKiom1cuLMSCOmXzAAAwnUi9x_U781.png


由于所有的SESSION卡在A,所以断定应该是检查数据的过程出现问题。于是进行查看。

锁定原因:

红色区块检查数据的代码中,抛出了一个运行时的异常。

很可惜,外部的手动管理的事务压根没有做try catch进行回滚事务操作。异常被线程池捕获处理,连接并没有返回到连接池。


最后还是要澄清一下,这代码不是我写的。。。。。


在无法实时查看JVM的情况下,DBE团队提供的数据起了很大的帮助。

追踪泄露了的SESSION最后执行的SQL,也是一个非常好的起点。