远程JMX连接

时间:2009-05-07 13:12:40

标签: java jmx jconsole

我正在尝试打开与远程计算机上运行的Java应用程序的JMX连接。

应用程序JVM配置有以下选项:

  • com.sun.management.jmxremote
  • com.sun.management.jmxremote.port = 1088
  • com.sun.management.jmxremote.authenticate =假
  • com.sun.management.jmxremote.ssl =假

我可以使用jconsole或jvisualvm使用localhost:1088进行连接。 但是我无法使用远程计算机上的xxx.xxx.xxx.xxx:1088进行连接。

服务器之间或操作系统之间没有防火墙。但是为了消除这种可能性我telnet xxx.xxx.xxx.xxx 1088并且我认为它连接起来,因为控制台屏幕变成空白。

这两台服务器都是Windows Server 2008 x64。尝试使用64位JVM和32位,都不起作用。

12 个答案:

答案 0 :(得分:109)

如果它出现在Linux上,问题是 localhost是环回接口,您需要将应用程序绑定到网络接口

您可以使用netstat确认它未绑定到预期的网络接口。

您可以通过使用系统参数java.rmi.server.hostname="YOUR_IP"调用程序来作为环境变量或使用

来完成此工作
java -Djava.rmi.server.hostname=YOUR_IP YOUR_APP

答案 1 :(得分:59)

我花了一天多的时间试图让JMX从localhost外部工作。似乎SUN / Oracle未能就此提供良好的文档。

确保以下命令返回真实的IP或HOSTNAME。如果它确实返回类似127.0.0.1,127.0.1.1或localhost的内容,它将无法工作,您将不得不更新/etc/hosts文件。

hostname -i

以下是从外部启用JMX所需的命令

-Dcom.sun.management.jmxremote 
-Dcom.sun.management.jmxremote.authenticate=false 
-Dcom.sun.management.jmxremote.ssl=false 
-Dcom.sun.management.jmxremote.port=1100
-Djava.rmi.server.hostname=myserver.example.com

您假设的地方,myserver.example.com必须与hostname -i返回的内容相匹配。

显然,您需要确保防火墙不会阻止您,但我几乎可以肯定这不是您的问题,问题是未记录的最后一个参数。

答案 2 :(得分:19)

在我使用Tomcat和Java 8进行的测试中,除了为JMX指定的端口之外,JVM还打开了一个临时端口。以下代码解释了我;如果您遇到JMX客户端(例如VisualVM未连接的问题),请尝试尝试。

-Dcom.sun.management.jmxremote.port=8989
-Dcom.sun.management.jmxremote.rmi.port=8989

另见Why Java opens 3 ports when JMX is configured?

答案 3 :(得分:12)

http://blogs.oracle.com/jmxetc/entry/troubleshooting_connection_problems_in_jconsole

如果您尝试访问NAT后面的服务器 - 您很可能必须使用选项启动服务器

-Djava.rmi.server.hostname=<public/NAT address>

以便发送到客户端的RMI存根包含服务器的公共地址,允许客户从外部访问它。

答案 4 :(得分:8)

它接近你的结尾报价来得太早了。它应该在最后一个参数之后。

这个技巧对我有用。

我注意到一些有趣的事情:当我使用以下命令行启动我的应用程序时:

java -Dcom.sun.management.jmxremote.port=9999
     -Dcom.sun.management.jmxremote.authenticate=false
     -Dcom.sun.management.jmxremote.ssl=false

如果我尝试使用jconsole从远程计算机连接到此端口,则TCP连接成功,一些数据在远程jconsole和部署我的MBean的本地jmx代理之间交换,然后,jconsole显示连接错误消息。我执行了wireshark捕获,它显示来自代理和jconsole的数据交换。

因此,这不是网络问题,如果我使用或不使用java.rmi.server.hostname系统属性执行netstat -an,我有以下绑定:

 TCP    0.0.0.0:9999           0.0.0.0:0              LISTENING
 TCP    [::]:9999              [::]:0                 LISTENING

这意味着在两种情况下,在端口9999上创建的套接字都接受来自任何地址上任何主机的连接。

我认为此系统属性的内容在连接时使用,并与代理用于与jconsole通信的实际IP地址进行比较。如果这些地址不匹配,则连接失败。

使用jconsole从同一主机连接时,我没有遇到此问题,仅使用真实的物理远程主机。所以,我认为只有当连接来自“外部”时才会进行此检查。

答案 5 :(得分:5)

非常感谢,它的工作原理如下:

java -Djava.rmi.server.hostname = xxx.xxx.xxx.xxx -Dcom.sun.management.jmxremote -Dcom.sun.management.jmxremote .ssl = false -Dcom.sun.management.jmxremote.authenticate = false -Dcom.sun.management.jmxremote.port = 25000 -jar myjar .jar

答案 6 :(得分:5)

对我有用的是将/ etc / hosts设置为将主机名指向ip,而不是指向loopback接口,而不是重启我的应用程序。

cat / etc / hosts

127.0.0.1      localhost.localdomain localhost
192.168.0.1    myservername

这是我的配置:

-Dcom.sun.management.jmxremote.port=1617 
-Dcom.sun.management.jmxremote.ssl=false 
-Dcom.sun.management.jmxremote.authenticate=false

答案 7 :(得分:1)

我知道这个线程已经很老了,但是还有一个额外的选项可以极大地帮助您。看到这里:https://realjenius.com/2012/11/21/java7-jmx-tunneling-freedom/

-Dcom.sun.management.jmxremote.rmi.port=1099

答案 8 :(得分:0)

我有同样的问题,我将任何与本地主机名匹配的主机名更改为0.0.0.0,在我这样做之后似乎可以正常工作。

答案 9 :(得分:0)

要启用JMX remote,请将以下VM参数与JAVA Command一起传递。

    -Dcom.sun.management.jmxremote 
    -Dcom.sun.management.jmxremote.port=453
    -Dcom.sun.management.jmxremote.authenticate=false                               
    -Dcom.sun.management.jmxremote.ssl=false 
    -Djava.rmi.server.hostname=myDomain.in

答案 10 :(得分:0)

尝试一下,我测试了如何在docker容器中访问JMX

-Dcom.sun.management.jmxremote = true -Djava.rmi.server.hostname =本地主机 -Dcom.sun.management.jmxremote.port = 16000 -Dcom.sun.management.jmxremote.rmi.port = 16000 -Dcom.sun.management.jmxremote.authenticate = false -Dcom.sun.management.jmxremote.ssl = false

然后

$ jconsole localhost:16000

答案 11 :(得分:-10)

尝试使用高于3000的端口。