2014-07-09 69 views
0

我知道有些类似的问题已经回答了这个问题,但是我已经阅读过这些内容,但我仍然遇到麻烦。调试RMI连接

我有一台服务器和一台使用RMI的客户端互相连接。客户在大学,服务器在家。这样做是因为我可以完全控制家中的任何防火墙,但不是在大学,我觉得这会给我最好的工作机会。

我在同一台机器上使用“localhost”测试了它们,这很好(包括home和uni)。然后,我将服务器移动到运行Windows Server 2012的主机上的VM上。我可以远程桌面到该VM,因为它被设置为桥接连接并设置了端口转发。我也转发端口1099的服务器有权在主本的顶部:

System.setProperty("java.rmi.server.hostname", "localhost"); 
setRegistry(LocateRegistry.createRegistry(1099)); 
System.setSecurityManager(new RMISecurityManager()); 
Naming.rebind("rmi://localhost/" + AUTH_OBJECT_BINDING, server); 

安全管理器使用其中有一个security.policy档案,现在:

grant { 
     permission java.security.AllPermission; 
}; 

当我尝试我的客户端连接到服务器,有取代“本地主机”的命名查找与我家IP在客户端,并通过防火墙已经允许Java和设置端口转发,我得到这个:

java.rmi.ConnectException: Connection refused to host: xxx.xxx.xxx.xxx; nested exception is: 
    java.net.ConnectException: Connection timed out: connect 

其中xxx.xxx.xxx.xxx是我正确的主IP地址。

因此,为了测试问题出在哪里,我在服务器虚拟机上运行客户端,但不是使用本地主机,而是使用我的外部IP。这连接和工作。因此,因为我可以连接使用我的外部IP(从217.137 ...开始),我认为服务器正在接受连接。

我认为这意味着来自大学的出站连接存在问题。这是唯一的问题吗?我想排除一切。不幸的是,我无法访问另一个不在家或者不是的网络,但是使用我在家里的外部IP进行测试应该是一样的。

如果是这样,我可以在我的家用机器上建立一个SSH服务器,我知道这个服务器可以在大学内使用,也许可以使用腻子和隧道,任何指导,或者甚至可能真的有帮助。

只是要清楚,我的问题分为两部分: 1)它可能是在大学阻止我连接到我的服务器的出站规则。 2)如果是这样,我该如何设置好与RMI协同工作?

任何帮助真的很感激。

回答

1
System.setProperty("java.rmi.server.hostname", "localhost"); 

这绝对不行。它需要设置为服务器的公用IP或主机名,通过它可以通过Internet访问它。

什么你所做的是强迫每到包含的“localhost”作为它的目标地址的存根,如果客户端在同一个本地主机作为服务器,这将正常工作,而不是其他。它需要是客户端可以用来连接到服务器的东西。

您还需要在通常情况下通过超级(1099)在端口1099上导出远程对象,这又意味着您必须通过LocateRegistry.createRegistry()运行注册表,确保存储结果在一个静态变量,所以它不会被垃圾收集。

+0

嗨,谢谢你。所以我把它设置为217.137.xxx.xxx(我的IP)。 \t \t \t System.setProperty(“java.rmi.server.hostname”,“217.137.xxx.xxx”); 这是有道理的。 在我的Naming.rebind上,我仍然使用它(因为它需要是本地主机): Naming.rebind(“rmi:// localhost /”+ AUTH_OBJECT_BINDING,server); 现在,当我尝试使用localhost或我的外部IP从我的客户端(现在基于相同的VM)进行连接时,我得到连接拒绝异常。 – ThePerson

+1

是您的公开IP地址217.137.xxx.xxx?你是否在端口1099上导出远程对象?你在lookup()上得到异常吗?或执行远程方法时? – EJP

+0

217.137.xxx.xxx是我的公开地址。我知道这是正确的,因为我目前正在将它用于远程桌面,并且它工作正常(我现在在uni)。当我使用loopup时,我没有得到异常,但是当我调用返回的第一个方法时,我得到它。例如,我的客户机具有: authObject =(InterfaceAuth)Naming.lookup( “RMI://217.137.xxx.xxx/” + AUTH_OBJECT_BINDING) 然后 会话= authObject.Authenticate( “用户”, “通”) ; 然后我从这行中得到异常,java.rmi.ConnectException:连接拒绝主机:217.137.xxx.xxx; – ThePerson

0

我手边没有任何特定的文档,但据我所知RMI不适用于NAT。

我假设你仍然能够从你的网络内部连接到服务器,因为你的路由器使用NAT环回。

+0

感谢您的评论。我的家用机器上的虚拟机使用直接(桥接)连接,所以我认为它应该没问题?或者我可能在这里错过了一些东西。 – ThePerson

+0

'RMI与NAT无法正常工作'是错误的。 – EJP

+0

@EJP就我所知,在NAT后面运行RMI服务器只有在java.rmi.server.hostname属性设置为解析为私有内部IP的域名(不是IP)时才起作用NAT网络内部以及面向公众的网络外的IP。 – rthur