【问题标题】:High memory usage when using Hibernate使用 Hibernate 时内存使用率高
【发布时间】:2014-08-13 02:09:17
【问题描述】:

我编写了一个在 linux 服务器上运行 java 的服务器端应用程序。 我使用休眠打开数据库会话,使用本机 sql 查询它,并始终通过 try、catch、finally 关闭此会话。

我的服务器以非常高的频率使用休眠查询数据库。

我已经将 MaxHeapSize 定义为 3000M,但它通常在 RAM 上使用 2.7GB,它可以减少但比增加慢。有时它会增长到 3.6GB 的内存使用量,超过我在启动时定义的 MaxHeapSize。

当使用的内存为 3.6GB 时,我尝试使用 -jmap 命令转储它并得到一个大小仅为 1.3GB 的 heapdump。

我用eclipse MAT分析一下,这里是MAT的支配树 我认为休眠是问题所在,我有很多这样的 org.apache.commons.collections.map.AbstractReferenceMap$ReferenceEntry。它可能无法通过垃圾回收处理,或者可以但很慢。

我该如何解决?

【问题讨论】:

    标签: java hibernate memory-leaks out-of-memory heap-dump


    【解决方案1】:

    您的 IN 查询列表中有 250k 个条目。即使是本机查询也会使数据库瘫痪。出于性能原因,Oracle 将 IN 查询列表限制为 1000,因此您应该这样做。

    给它更多的 RAM 并不能解决问题,您需要通过使用分页将您的选择/更新限制为最多 1000 个条目的批次。

    Streaming 也是一个选项,但对于如此大的结果集,keyset pagination 通常是最佳选项。

    如果您可以在数据库中完成所有处理,那么您就不必将 250k 记录从数据库移动到应用程序。许多 RDBMS 提供高级过程语言(例如 PL/SQL、T-SQL)是有充分理由的。

    【讨论】:

    • 你能再教我一点吗?我对oracle数据库交互的经验很少。
    • 您需要获取 N 个条目,更新它们然后获取下一批,依此类推。
    • 我仍然很困惑,在我的查询“UPDATE .. WHERE .. IN (...)”中,IN 查询列表很小,无法达到 1000。当我扩展到叶子时eclipse MAT中的支配树,我找到了我的选择查询(我的代码中的'sqlQueryCheckSet'),很多,我认为只有它
    • 查看Hibernate issue。将“hibernate.query.plan_cache_max_soft_references”和“hibernate.query.plan_cache_max_strong_references”设置为一些适当的值。
    • 太棒了。那么问题就得到了解答。
    【解决方案2】:

    感谢Vlad Mihalcea 提供指向Hibernate issue 的链接,这是休眠中的错误,已在 3.6 版中修复。我只是将我的休眠版本 3.3.2 更新到版本 3.6.10,使用“hibernate.query.plan_cache_max_soft_references”(2048)、“hibernate.query.plan_cache_max_strong_references”(128)的默认值,我的问题就消失了。不再有高内存使用。

    【讨论】:

    • 我面临着类似的性能问题,您将哪个模块升级到 3.6.10
    【解决方案3】:

    请注意,尽管可以配置和限制 queryPlanCache 中的对象数量,但拥有那么多可能并不正常。

    在我们的例子中,我们在 hql 中编写类似于这样的查询:

    hql = String.format("from Entity where msisdn='%s'", msisdn);
    

    这导致 N 个不同的查询进入 queryPlanCache。当我们将此查询更改为:

    hql = "from Blacklist where msisnd = :msisdn";
    ...
    query.setParameter("msisdn", msisdn);
    

    queryPlanCache 的大小从 100Mb 显着减少到几乎为 0。第二个查询被转换为一个单一的preparedStament,导致缓存中只有一个对象。

    【讨论】:

      猜你喜欢
      • 2012-05-31
      • 1970-01-01
      • 2011-03-31
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-05-05
      • 1970-01-01
      相关资源
      最近更新 更多