Java 堆大小快速增加的spring启动应用程序

Java 堆大小快速增加的spring启动应用程序,java,mongodb,hibernate,spring-boot,jvm,Java,Mongodb,Hibernate,Spring Boot,Jvm,我使用mongoDB和hibernate for MySQL在spring boot上安装了应用程序。 应用程序的堆大小在生产中不断增加。我已经提供了最大堆大小为24GB,这已经是巨大的了。现在使用的堆已达到23GB。 将如此巨大的内存进行堆转储是否有好处,是否会因为它是实时应用程序而影响性能 另一种检测相同内存泄漏的方法? 还是其他分析hibernate或mongo指标的方法 尝试在jprofiler或jvisualvm中查看堆内存。其中一个选项是,堆将占用您提供的所有内存,但只使用其中的一部

我使用mongoDB和hibernate for MySQL在spring boot上安装了应用程序。 应用程序的堆大小在生产中不断增加。我已经提供了最大堆大小为24GB,这已经是巨大的了。现在使用的堆已达到23GB。 将如此巨大的内存进行堆转储是否有好处,是否会因为它是实时应用程序而影响性能

另一种检测相同内存泄漏的方法?
还是其他分析hibernate或mongo指标的方法

尝试在jprofiler或jvisualvm中查看堆内存。其中一个选项是,堆将占用您提供的所有内存,但只使用其中的一部分。一般来说,这取决于垃圾收集器算法。我建议您执行以下步骤:

1) 检查heap占用的内存是否被实际使用(您可以在jprofiler或jvisualvm中看到)。如果应用程序占用了所有内存,但没有使用它,那么可以使用xmxjvm参数使用一些合理的值来限制它

2) 查看加载和空闲状态下的内存使用情况。看到区别了吗。根据您所执行的操作,内存中可能有一些对象,但它们应该随时收集


3) 如果它真的是泄漏的,并且您看到jvm保留的内存被真正使用,并且从未释放过,那么请进行内存转储,看看那里有什么类型的对象(再次尝试jprofiler或jvisualvm)。这将为您提供一个查找的线索。

是的,进行堆转储将“冻结世界”,并从本质上导致生产中断,我们不建议这样做。如果您使用的是Spring Boot,那么您的构建中是否包含了执行器?它不会提供堆度量,但会提供其他有用的东西。内存泄漏不太可能发生在hibernate或mongo中,更可能是您实现缓存或类似的方式。堆是否也在dev/qa/uat中逐渐增长?在那里进行堆转储,并分析其想法?另一个建议是,您是否在启用jmx的情况下运行?您可以尝试使用jconsole连接到它,看看是否有任何有用的MBean被公开。我确实启用了jmx,但在那里找不到任何有用的MBean,您能举一个例子吗?我应该在这里寻找什么,因为它显示了3个选项:“属性”、“操作”、“通知”。@Matt由于没有流量,无法在stg/dev上生成。应用程序主要由JMS监听器和spring调度程序组成。您是否从JMS监听器中读取到一个内部无界队列中,对该队列执行一些处理,并写入hibernate/mongo?如果JMS使用者没有背压(您将无法像从JMS消费一样快速地向数据库写入数据),那么这可能会导致内存泄漏。你能在stg/dev上快速生成模拟流量的应用程序吗?就我个人而言,这将是我的下一步。您希望能够在dev上重现这个问题,而不是在Production中进行调试,这是一个很好的观点-JVM最终将填充您提供给它的所有堆,但不一定使用所有堆,而且不一定会有崩溃的危险吗?如何在负载和空闲状态下查看内存使用情况?@Ionwolf这取决于您的应用程序的功能,即如果它是web服务,您可以生成一些负载,例如30个线程对某个服务执行100次调用(例如使用jmeter),然后查看图片。如果它是实时的,你可能会在白天或晚上有一些时间,因为系统使用不多。否则,您将不得不在暂存甚至本地环境中进行实验。这似乎是hibernate的查询计划缓存的问题,因为我将堆转储作为暂存,它包含带有sql查询的char[]。有没有限制或禁用此缓存的建议?