开启远程Debug

# jdk < java9 之前(默认监听所有)
-Xdebug -Xrunjdwp:server=y,transport=dt_socket,address=4000,suspend=n

# jdk >= java9(默认只监听本地, 所以要 *:端口, 开启远程)
-Xdebug -Xrunjdwp:server=y,transport=dt_socket,address=*:4000,suspend=n

开启 JMX

-Dcom.sun.management.jmxremote
-Dcom.sun.management.jmxremote.port=9010
-Dcom.sun.management.jmxremote.local.only=false
-Dcom.sun.management.jmxremote.authenticate=false
-Dcom.sun.management.jmxremote.ssl=false

开启 Jstatd

只有开启这个, 才能在 visualVM 里使用 visualGC

vim /tmp/jstatd.all.policy

grant codebase "file:${java.home}/../lib/tools.jar" {
   permission java.security.AllPermission;
};


然后启动 jstatd:

jstatd -J-Djava.security.policy=/tmp/jstatd.all.policy  -J-Djava.rmi.server.hostname=${你的外网IP}

Go

执行完上面的命令后, 就可以进行远程 debug 和 查看远程的 JVM 状态了.

打开 VisualVM, 添加 Remote (填写IP等信息), 然后在该IP主机下, 右键如下图:

img

选择 Add Jstatd Connection , 然后添加个 default 选项, 这样子 VisualVM 就会自动列出当前所有 java 进程了. 这时就可以在 VisualVM 中的 VisualGC 页看到可视化GC的信息了.

自动化脚本

为了方便使用, 自己写了个自动化脚本, 放在 Github gist

在配置好 JAVA_HOME 环境变量的前提下, 直接执行该脚本即可.

VisualGC 界面的字段解释

https://www.oracle.com/technetwork/java/visualgc-136680.html#output-format

  • Compile Time : 将 Java byte code 编译为 native code 的总耗时
  • Class Loader Time : class loading 以及 unloading 活动的总耗时
  • GC Time : GC 活动的总耗时
  • Eden Space : 显示 Eden Space 随时间的使用情况.例子: Eden Space(599.00M, 599.00M): 365.11M, 33984 collections, 2m 28.07s
    • Eden Space(最大容量,当前容量)当前大小, Young GC 次数, Young GC 总耗时
  • Survivor 0 和 Survivor 1 : 同理. (最大容量, 当前容量) 当前大小
  • Old Gen : 显示 Full GC 的次数和总耗时. (最大容量, 当前容量)当前大小
  • Perm Gen : 它没有独立的 收集器, 它是跟随 Old Gen 一起 GC 的.