Java RMI远程对象转换/状态

时间:2012-12-17 21:56:18

标签: java rmi

我有一个RMI应用程序,详情如下。服务器知道它正在创建DocumentProvider对象,并使用Document接口将对该对象的引用传递给客户端。当客户端将Document对象传递给服务器时,服务器不能再将其转换为DocumentProvider,尽管这是服务器最初创建的内容。

是否有办法进行此类转换,即服务器知道它正在创建具有更多内部功能的Document的特定实现(在本例中为InternalClass serverInfo),并希望在其实现中访问这些附加功能Document函数(在本例中为“doCast()”函数)。

另一种询问方式:服务器创建DocumentProvider对象后,该对象是否位于服务器上?如果是这样,我怎样才能给客户提供参考呢? InternalClass serverInfo; part不可序列化,不能传输到客户端。 (有点像文件句柄等,虽然我可以保留它并在DocumentProvider类中管理它。)

//Interface
public interface Document extends extends java.rmi.Remote {
        public String doSomething()  throws java.rmi.RemoteException;
        public String doCast()  throws java.rmi.RemoteException;
}

//The server:
    public class DocumentProvider extends java.rmi.server.UnicastRemoteObject implements java.rmi.Remote, Document {
        InternalClass serverInfo;

        public String doSomething()  throws java.rmi.RemoteException {
            return "DocumentProvider doing something";
        }
        public String doCast(Document d)  throws java.rmi.RemoteException {
            DocumentProvider d2 = (DocumentProvider) d; // this cast fails, even when d was a DocumentProvider class
            // then access d.serverInfo, etc.
        }
    }

public interface DocumentFactory extends extends java.rmi.Remote {
        public Document createDocument() throws java.rmi.RemoteException;
}
public class DocumentProvider extends java.rmi.server.UnicastRemoteObject implements java.rmi.Remote, DocumentFactory {
    public Document createDocument() throws java.rmi.RemoteException {
        return new DocumentProvider();
    }
}

//Client app:
main()... {
    DocumentFactory dFactory = (lookup/resolve this; this works ok);
    Document dMain = dFactory.createDocument();
    dMain.doCast(dMain);  // this fails because
}

详细说明,“InternalClass serverInfo”是一个不可序列化的第三方“句柄”,我必须以某种方式将其状态保存在服务器中,所以主要的问题是如何做到这一点,同时返回对远程对象的引用,允许客户端通过接口中定义的远程调用“操纵”该内部对象。 (另一个更简单的例子:如果serverInfo是文件句柄,我允许客户端通过Document接口执行“搜索”和“读取”功能)

1 个答案:

答案 0 :(得分:1)

远程对象作为实现相同远程接口的存根传递和返回。因此,转换到实际的远程对象类是不可能的,并且尝试远程执行它会更不明智。只需使用存根作为接口的实例。如果这还不够,那么你的设计就会出现问题。