Linux入门实践笔记(七)——云服务器中配置Java项目的JMX连接失败问题解决记录

内容

  笔者在阿里云服务器中配置Java项目的JMX远程连接,在确认JVM参数、防火墙、阿里云安全组设置都无误后,使用JConsole等工具连接JVM时仍出现JMX连接失败的问题。笔者将该问题的解决方法记录成文,供网友遇到同样问题时能快速的处理。

版本

  操作系统: CentOS 7.2 64位

  JDK:1.8.0_181

说明

  转载请说明出处:Linux入门实践笔记(七)——云服务器中配置Java项目的JMX连接失败问题解决记录

  JMX连接的官方文档:https://docs.oracle.com/javase/8/docs/technotes/guides/management/agent.html

为何要开启JMX监控

  作为一名Java开发人员,大多数情况下,只要确保写好的代码功能能跑通即可,很少关注代码对CPU、内存、线程的资源依赖情况。但是如果出现了Out-Of-Memory等问题,或想监控Java项目的运行状况(比如在进行压力测试时),可以使用JMX客户端监控JVM的资源使用情况。常用的JMX客户端有JConsole、JMC、JVisualVM,这些都是JDK自带的工具。

开启JVM的JMX监控

  在启动jar包时添加com.sun.management.jmxremote.* 相关的JVM参数,该示例以7199为JMX远程监控的端口,不使用SSL安全连接,不启用账号密码认证:

[user@ServerA2 jars]$ java -Dcom.sun.management.jmxremote.port=7199 #供JMX客户端远程连接用的端口号 
-Dcom.sun.management.jmxremote.authenticate=false #关闭账号密码认证,不安全,仅在开发阶段使用
-Dcom.sun.management.jmxremote.ssl=false #关闭SSL
-Djava.rmi.server.hostname=106.117.142.x #指定本机供远程访问的IP地址,此处是本机的公网IP
-Xms512m -Xmx512m -jar zuul-1.0-SNAPSHOT.jar &

​ 其中-Djava.rmi.server.hostname参数一定要设置,否则连接失败。

云服务器JMX连接失败原因

  正确地配置了JVM参数后启动jar包,在本地仍然无法使用JMX Client访问云服务器上的JVM。笔者在阿里云提交了工单,经过长达两天时间多次沟通后终于得知JMX连接失败的原因。

  开启JMX远程监控管理功能后,JVM不仅会占用指定的com.sun.management.jmxremote.port配置的端口号7199,还会额外再开启两个随机的端口号用于通信。如果这两个随机的端口号没有开放访问,那么远程JVM Client还是无法连接到JVM的。

  执行netstat -nltp命令可以查看JVM进程监听的端口,本示例中启动的java进程的PID为15703,通过下面的查询可知需要额外放行的两个端口为41264和41665。

[user1@ServerA2 jars]$ netstat -nltp
#其中:-n表示表示输出中不显示主机,端口和用户名,-lb表示只显示监听listening端口,-t表示只显示tcp协议的端口,-p表示显示进程的PID和进程名称。
(Not all processes could be identified, non-owned process info
 will not be shown, you would have to be root to see it all.)
Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address           Foreign Address         State       PID/Program name
tcp        0      0 0.0.0.0:41264           0.0.0.0:*               LISTEN      15703/java
tcp        0      0 0.0.0.0:8881            0.0.0.0:*               LISTEN      15703/java
tcp        0      0 0.0.0.0:22              0.0.0.0:*               LISTEN      -
tcp        0      0 0.0.0.0:7001            0.0.0.0:*               LISTEN      15074/java
tcp        0      0 0.0.0.0:7101            0.0.0.0:*               LISTEN      15074/java
tcp        0      0 0.0.0.0:7199            0.0.0.0:*               LISTEN      15703/java
tcp        0      0 127.0.0.1:32000         0.0.0.0:*               LISTEN      -
tcp        0      0 0.0.0.0:41665           0.0.0.0:*               LISTEN      15703/java
tcp6       0      0 :::80                   :::*                   LISTEN      -

  将这两个端口号在安全组中放行后,远程JMX Client就可以正常访问JVM,真坑。

原文地址:https://www.cnblogs.com/lonelyJay/p/9997867.html