What they're testing
Whether you have a procedure, know which tools exist on a production box, and collect evidence BEFORE restarting.
The short answer~30 seconds
Collect evidence first, fix second — a restart erases the clues. I run top -H -p <pid> to find which thread is burning CPU, convert its id to hex, then jstack <pid> and search for the matching nid=0x… to see what that thread is doing. In parallel, jstat -gcutil rules out a GC death spiral rather than application code. Those two together separate the three usual causes.
The long answer
Three causes cover nearly everything. First, a GC death spiral: the heap is nearly full, full GCs run back to back reclaiming almost nothing, CPU is at 100% while the application barely progresses. The tell is jstat showing old-gen occupancy pinned high with the full-GC count climbing fast. Second, an infinite loop or an algorithm exploding on unusual input, visible directly in that thread's stack. Third, lock contention with threads spinning, usually obvious when jstack shows dozens of threads at the same line.
The procedural point is taking SEVERAL jstacks a few seconds apart, not one. One snapshot gives you a moment; three tell you which thread is STUCK in the same place — and that's the one worth investigating. If memory is suspected, jmap -dump:live before restarting, accepting that it causes a long pause, because without the dump you'll be standing in this exact spot again next time.
At senior level, a good answer also names what should be arranged BEFORE the incident: Java Flight Recorder running continuously at low overhead, so when something happens you already have the minutes leading up to it instead of starting to measure while everything burns. Always-on JFR costs about 1% and is one of the easiest trade-offs to justify in JVM operations.
One last thing: restarting is a legitimate action while users are affected — just do it after capturing the dumps. Restore service first, but don't let restoring it destroy your ability to prevent the next one. Getting that order right scores more than naming tools.
The first ten minutes, in order
top -H -p $PID # luồng nào ăn CPU? lấy TID thập phân
printf '%x\n' $TID # đổi sang hex để khớp với nid trong jstack
jstack $PID > /tmp/1.txt # chụp 3 lần, cách nhau 5 giây
jstat -gcutil $PID 1000 10 # O ổn định ở mức cao + FGC tăng = GC quay vòng
jcmd $PID GC.heap_info
jmap -dump:live,format=b,file=/tmp/heap.hprof $PID # trước khi restartWhat they'll ask next
?What if you can't SSH into the container?
kubectl exec if the image has a JDK; many images ship only a JRE and therefore no jstack — which is the argument for packaging diagnostics or enabling JFR up front. Failing that, kubectl debug with an ephemeral container sharing the process namespace.
?How do you tell GC from application code?
Look at thread names in top -H: G1's collector threads are GC Thread#n. If those are the CPU consumers, it's GC. Beyond that, a GC log via -Xlog:gc* shows frequency and how much was reclaimed — running constantly while reclaiming little is the clearest signal.
These lose points
- "Restart and keep an eye on it." That's an action, not a diagnosis, and it destroys the evidence.
- Naming tools without an order or a reason. The interviewer wants to hear a procedure.