加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 百科 > 正文

使用Oracle JDBC驱动程序12c的Tomcat 7上的内存泄漏 – oracle.j

发布时间:2020-12-12 13:14:05 所属栏目:百科 来源:网络整理
导读:我有一个部署到Tomcat 7.0.54的Web应用程序,它使用数据源连接到Oracle 11g数据库.数据源在META-INF / context.xml中配置,我将ojdbc7.jar放在 tomcat-install-dir / lib中.我使用JNDI查找来检索我存储在单例中的数据源,以便每个DAO类都可以使用它. 一切都按预
我有一个部署到Tomcat 7.0.54的Web应用程序,它使用数据源连接到Oracle 11g数据库.数据源在META-INF / context.xml中配置,我将ojdbc7.jar放在< tomcat-install-dir> / lib中.我使用JNDI查找来检索我存储在单例中的数据源,以便每个DAO类都可以使用它.

一切都按预期工作,但是当我取消部署应用程序(通过Tomcat管理器应用程序)时,我在日志中看到:

Oct 03,2014 3:06:55 PM org.apache.catalina.loader.WebappClassLoader clearReferencesThreads
SEVERE: The web application [/myapp] appears to have started a thread named [oracle.jdbc.driver.BlockSource.ThreadedCachingBlockSource.BlockReleaser] but has failed to stop it. This is very likely to create a memory leak.
Oct 03,2014 3:06:57 PM org.apache.catalina.startup.HostConfig undeploy
INFO: Undeploying context [/myapp]

当我调试时,我可以看到一旦访问数据库就会创建这个线程(通过数据源).

我的数据源配置:

<Context antiResourceLocking="false">
    <Resource name="jdbc/myapp" auth="Container" 
        type="javax.sql.DataSource" driverClassName="oracle.jdbc.OracleDriver" 
        maxActive="20" maxIdle="10" maxWait="-1"
        username="myuser" password="mypass"
        url="jdbc:oracle:thin:@myserver:1521:mysid"
        removeAbandoned="true" removeAbandonedTimeout="10" logAbandoned="true"
        validationQuery="SELECT 1 FROM DUAL"   
        testOnBorrow="true" testOnReturn="true" testWhileIdle="true"  
        timeBetweenEvictionRunsMillis="1800000" numTestsPerEvictionRun="3"  
        minEvictableIdleTimeMillis="1800000"
    />
</Context>

编辑

进一步的调查表明,无论在应用程序(或servlet)初始化期间是否访问数据源,都会出现问题.

实际上,只有在使用Oracle的JDBC驱动程序的12c版本(ojdbc6.jar或ojdbc7.jar)时才会创建有问题的线程,因此只存在问题.

如果我恢复使用ojdbc6.jar的11.2.0.4版本,则永远不会创建线程,并且永远不会出现内存泄漏警告.

我应该降级JDBC驱动程序(如https://stackoverflow.com/a/9177263/4105953中所述)吗?

解决方法

我找到了关于主题 here的冗长讨论.结论是它创建了“固定大小的内存泄漏”,即随后的重新部署不会增加内存泄漏.
我没有Oracle Support访问权限,但讨论中提到的错误ID是16841748(2013年5月,现在可能已解决).

一个可能的解决方法是在Tomcat通过在tomcat / conf / web.xml中配置为“load-on-startup”的自定义servlet启动时实际使用数据源一次(获取连接,执行虚拟查询,关闭连接).这应该启动Web驱动程序类加载器范围之外的Oracle驱动程序线程(另请参阅FAQ关于驱动程序线程),从而防止“固定大小的内存泄漏”.

请注意,MySQL JDBC驱动程序存在类似的问题,但有一个decent solution.对于最新版本的Oracle JDBC驱动程序(我不知道),可能存在这样的解决方案.

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读