garbage-collection - GC 图显示存在内存泄漏但无法在转储中跟踪
问题描述
我们的应用程序中有一个 Java Micorservice,它连接到 Postgres 和 Phoenix。我们使用的是 Spring Boot 2.x。
问题是我们正在为我们的应用程序执行大约 8 小时的耐久性测试,我们可以观察到使用的堆在不断增加,尽管我们使用了推荐的 VM 参数建议,看起来像是内存泄漏。我们分析了堆转储,但是根本原因对我们来说并不完全清楚,一些专家可以根据结果提供帮助吗?
我们实际使用的 VM 参数是:
-XX:ConcGCThreads=8 -XX:+DisableExplicitGC -XX:InitialHeapSize=536870912 -XX:InitiatingHeapOccupancyPercent=45 -XX:MaxGCPauseMillis=1000 -XX:MaxHeapFreeRatio=70 -XX:MaxHeapSize=536870912 -XX:MinHeapFreeRatio=40 -XX: ParallelGCThreads=16 -XX:+PrintAdaptiveSizePolicy -XX:+PrintGC -XX:+PrintGCDateStamps -XX:+PrintGCDetails -XX:+PrintGCTimeStamps -XX:StringDeduplicationAgeThreshold=1 -XX:+UseCompressedClassPointers -XX:+UseCompressedOops -XX:+UseG1GC - XX:+使用字符串去重
我们期望使用的堆在 GC 日志中应该是平坦的,但是内存消耗没有释放并且它不断增加。
解决方案
我不确定您在上面使用的是哪个工具,但我会在堆中寻找支配者层次结构。Eclipse MAT是分析堆转储的好工具,它可以为您指明实际持有内存的方向,您可以决定是否要将其归类为泄漏。不管你贴什么标签,如果应用程序在一段时间后因为内存不足而崩溃,那么这是一个问题。
该博客还讨论了诊断此类问题。
推荐阅读
- c# - 在退出 C# 窗口应用程序之前运行代码
- java - 这种方法的测试用例是什么?
- python - 上传的文件/块正在消失
- python - 在 Python 中使用 sqlite3 内存模式作为缓存是个好主意吗?
- flutter - Flutter - 对齐和包装问题
- .net - mac/linux `dotnet build` 没有找到框架“.NETFramework..”的参考程序集
- c - 这个 C 程序可以工作,但编译会产生错误。为什么?
- java - 为什么 this.getClass().getName() 会产生与 StackTraceElement.getClassName() 不同的结果?
- java - Java - 从 Spring Boot 应用程序中获取变量
- python - 我如何根据键值将python dict排序为嵌套列表