我面临了一个有趣的问题,尝试分析在Docker容器和主机上运行的Java应用程序的内存消耗。
- Java应用程序是在Jetty服务器9.4.9上的Web应用程序
- Java版本:1.8
- 主机:MAC
- Docker镜像:jetty:9.4-jre8
- Docker守护程序版本为18.03.1-ce。
在主机上,我使用Yourkit工具来分析内存消耗。
对于docker容器docker stats <docker id/name>
我得到的是,在MAC上,yourkit显示了50M的非堆大小+大约40M的堆大小,总共约100M
而当我部署并在容器上运行相同的war文件时,统计数据显示我有200M
CONTAINER ID NAME CPU % MEM USAGE / LIMIT MEM % NET I/O BLOCK I/O PIDS
879fb113ca8d jetty-app 0.19% 214.6MiB / 1.952GiB 10.74% 1.49MB / 88.9kB 31.7MB / 6.42MB 29
有人能解释一下这个现象吗?
假设stats
提供了错误的结果,我尝试使用--memory
标志限制容器的内存,但效果不大,我仍然遇到了OOM。
提前感谢。
yourkit
和docker stats
的精确输出可能会很有用。 - Jaroslaw Pawlakdocker stats
可能包括线程堆栈使用的内存 - 默认情况下每个线程使用1MB,不包括在堆内存或非堆内存中,因此建议在yourkit中检查线程计数。3. yourkit显示的堆内存看起来有点奇怪 - 尽管应用程序仅使用了25MB的堆内存,但它可能保留了更多内存(绿线看起来像75MB)。 - Jaroslaw Pawlak