Our dockerized Java application JVM Heap usage sometimes increases too much We can check it from JVM Prometheus Exporter.
- Run Test App
docker run -it --rm pamir/jvm-cases SingleThreadHighMemoryUsage
- Check, that our app is not idle(%CPU > 0.0):
top -c -p $(pgrep -d',' -f java)
- Get id of container with our application(java application.jar ...):
docker ps
- Run container with jattach utility:
docker run --rm -it \
--net=container:8b0970e1aa99 \
--pid=container:8b0970e1aa99 \
-v /tmp:/tmp \
--privileged \
adriantodt/alpine-zlib-jattach \
/bin/sh
- Dump Heap with jattach
jattach 1 heapdump /tmp/memoryleak1.hprof
jattacj 1 heapdump /tmp/memoryleak2.hprof
- Be careful the dump files are not in in on jattach container. They are on java container's tmp directory
ls -lart /tmp
- Copy Dump files from java container to host machine
docker cp 8b0970e1aa99:/tmp/memoryleak1.hprof /tmp/memoryleak1.hprof
docker cp 8b0970e1aa99:/tmp/memoryleak2.hprof /tmp/memoryleak2.hprof
-
Download Memory Dump Analzyer Tool
http://www.eclipse.org/mat/ -
Open Histogram and sort by retained heap size
-
Investigate suspected thread which pressures memory
-
Find out what is consuming too much memory. In this type of scenerio UsernamePassword String array can make memory pressure. This pattern is Single Thread High Memory Usage. I have seen this too much when developers forget to add where clause. We can extract the query from the heap dump in such cases
- drop capabilities
- Add Reference to Charlie Hunt Book Java Performance
- Refer to Source Code
- Convert this simple to hibernate/MYSQL scenrio