3

使用RMI将String对象从WebAppA传递给WebAppB。WebAppB是RMIServer,而WebAppA是RMIClient。我在WebAppB中添加了ContextListener,这样在tomcat中初始化上下文时rmi服务立即启动。并且在tomcat的contextDestroyed方法中我正在尝试使用以下语句关闭/关闭 rmi:

unexportObject(remoteObj,true);
LocateRegistry.getRegistry(3232).unbind("MessagePath"); //MessagePath - name of the remote reference

但即使在执行上述语句之后,rmi 仍在端口 3232 处侦听传入请求。我在命令提示符下使用“netsat -ano”看到了这一点。请帮我关闭 RMI 服务。

4

3 回答 3

1

getRegistry 只返回一个存根,所以在 unexportObject 中使用 createRegistry 返回的实例。但是,在我的情况下,这也无济于事-注册表不再处于活动状态,但套接字仍处于打开状态并正在侦听:-(

于 2009-10-14T14:53:20.183 回答
0

createRegistry当您尝试关闭注册表时将无法正常工作。

Registry registry = LocateRegistry.createRegistry(3232);

这将BindException在注册表已经运行时抛出。所以你不能创建对象来使用它

UnicastRemoteObject.unexportObject(registry, true);

但是,即使您使用

Registry registry = LocateRegistry.getRegistry(3232);

您只获得了存根,它不能用作取消导出对象的参数。

它让我担心的原因是因为我只希望在我可以检查它尚未启动的情况下启动注册表。而且我还没有找到一种方法来做到这一点!

于 2009-10-17T02:57:48.427 回答
-1

我找到了一种从任何进程关闭注册表的方法(为此,关闭注册表中绑定的任何绑定进程)

任何扩展远程并且您最终想要终止的接口也应该扩展以下接口:

public interface PIDSupplierInterface extends Remote {
  String getPID() throws RemoteException;
}

然后,您创建的每个服务器类都必须实现 getPID() 作为其接口的一部分。然后您要做的就是返回进程 ID。适用于 Windows 的谷歌“getpids”,或访问此处:www.jroller.com/santhosh/entry/get_current_java_process_id。据我了解,对于 Linux,获取 PID 更简单。然后(在 Windows 中)你想去

String PID = myServer.getPID();
String[] a_command = { "taskkill", "/pid", PID };
Runtime.getRuntime().exec(a_command, envp, dir);

要杀死注册表本身的 PID,首先,在启动注册表时(以编程方式),只需执行

PIDSupplierInterface stub = PIDSupplierInterface)UnicastRemoteObject.exportObject( 
 new PIDSupplierServer(), 0);
reg.bind( "regKiller",  stub );

其中 PIDSupplierServer 是一个仅实现 PIDSupplierInterface 的类。

然后,当您想从任何进程中终止 RMI 注册表时,只需执行

PIDSupplierInterface regProcess = (PIDSupplierInterface)reg.lookup( "regKiller" );
String regPID = regProcess.getPID();
String[] a_command = { "taskkill", "/pid", regPID };
Runtime.getRuntime().exec(a_command, envp, dir);

reg 已从您的系统中消失。还是由于某种原因您的问题更复杂?欢迎任何意见。

于 2011-02-10T19:13:38.993 回答