1. Java RMI
Java Remote Method Invocation(Java远程方法调用)允许程序员创建分布式Java技术为基础的应用,可以调用不同JVM远程对象上的远程方法。RMI使用对象序列化去marshal(编码),unmarshal(解码)参数进行,不截断类型,支持面向对象的多态性。
2. Stub
RMI相当于一个代理模式。客户对象想要调用远程服务对象上的远程方法,我们需要一些辅助对象。这些辅助的对象使客户就像在调用本地对象的方法一样。客户对象调用客户辅助对象上的方法,仿佛客户辅助对象就是真正的服务。而客户辅助对象负责为我们转发这些请求,但是客户辅助对象不是真正的远程服务。虽然操作很像,但是不具有真正远程服务对象的方法逻辑。在服务端,服务辅助对象从客户辅助对象中接受请求,将调用的信息解包,然后调用真正服务对象上的真正方法。服务辅助对象从服务中得到返回值,将它打包,然后返回客户辅助对象,客户服务对象对信息解包,最后将返回值交给客户端。
Stub(存根)就相当于这里的客户辅助对象。存根将所需要的参数进行编码后传递给远程方法,并将调用结果或者异常传递给客户端。从JDK1.5开始,存根类可以采用动态代理的方式自动生成。在这之前,必须使用rmic工具手动创建。
3. java.rmi.Remote
3.1 扩展java.rmi.Remote接口
Remote是一个标记接口,没有任何方法,所有远程服务对象必须间接或者直接的扩展Remote接口。由于远程服务对象可以被其他的JVM调用,所有可以实现一个或多个远程接口。如果远程服务对象被同时的访问,必须在其实现中保证线程的安全。
public interface MyRemote extends java.rmi.Remote{}
3.2 接口声明中的所有方法都将抛出RemoteException异常。
客户调用远程接口的stub上的方法,而stub底层调用了网络和I/O,所以可能会发生各种异常,所以必须声明远程异常来解决。java.rmi.RemoteException继承自java.io.IOException。
public interface MyRemote extends Remote{
public String sayHello() throws RemoteException;
}
3.3 远程方法的变量和返回值必须是原语类型或者是可序列化类型。
这不难理解,因为远程方法的变量必须被打包并通过网络发送。(所以,在传送自己定义的类时,必须保证实现Serializable接口)
4. java.rmi.RemoteException
RemoteException继承自java.io.IOException。它是一个检查型异常,通常用来标识:通信失败、远程调用参数/返回值在编码(marshalling)/解码(unmarshalling)过程中出错,协议错误。
5. java.rmi.server.RemoteObject
RemoteObject类实现远程对象的java.lang.Object 行为,并提供了远程对象默认的hashCode、equals 和 toString 方法实现。创建远程对象并将其导出(使远程对象具有某些"远程的"功能)所需的方法由类UnicastRemoteObject 和 Activatable 提供。
6. java.rmi.registry.Registry
Registry是简单远程对象注册表的一个远程接口(默认的端口号为1099
),它提供绑定和查找的功能。其内部维护了一个名到对象的映射。LocateRegistry 用于获得对特定主机(包括本地主机)上引导远程对象注册表的引用,或用于创建一个接受对特定端口调用的远程对象注册表。 注意,getRegistry 调用并不实际生成到远程主机的连接。它只创建对远程注册表的本地引用,即便远程主机上没有正运行的注册表,它也会成功创建一个引用。LocateRegistry.createRegistry()方法在本机指定的端口上创建并发布一个registry远程对象。
7. 示例程序:
7.1 定义远程接口
public interface MyRemote extends Remote {
public String sayHello() throws RemoteException;
}
7.2 实现远程接口
public class MyRemoteImpl extends UnicastRemoteObject implements MyRemote{
private static final long serialVersionUID = -3510887331988311760L;
protected MyRemoteImpl() throws RemoteException {
} //这里必须抛出RemoteException异常,因为超类会抛出这个异常
@Override
public String sayHello() throws RemoteException {
return "server say hello to client";
}
}
7.3 用RMI Registry注册此服务
public class MyRemoteImpl extends UnicastRemoteObject implements MyRemote{
private static final long serialVersionUID = -3510887331988311760L;
protected MyRemoteImpl() throws RemoteException {
}
@Override
public String sayHello() throws RemoteException {
return "server say hello to client";
}
public static void main(String[] args) {
try {
MyRemote remote = new MyRemoteImpl();
Naming.bind("myRemoteServer", remote);
} catch (RemoteException e) {
e.printStackTrace();
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (AlreadyBoundException e) {
e.printStackTrace();
}
}
}
当注册这个实现对象时,RMI系统实际注册的是stub。
7.4 客户端定义
public class Client {
public static void main(String[] args) {
try {
MyRemote remote = (MyRemote)Naming.lookup("rmi://127.0.0.1/myRemoteServer");
System.out.println(remote.sayHello());
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (RemoteException e) {
e.printStackTrace();
} catch (NotBoundException e) {
e.printStackTrace();
}
}
}
启动:
1. 启动remiregistry服务(位于Java\jdk1.6.0_18\bin,启动的目录必须为你workspace的bin目录)
rmiregistry -J-Djava.rmi.server.codebase=file:/D:/FXworkspace/rmi/bin/
2. 执行MyRemoteImpl
3. 执行Client
结果输出:
server say hello to client
工作方式:
1)客户到RMI registry中寻找
2)RMI registry返回stub对象。
3)客户调用stub方法,就像stub是真正的服务对象一样。
注:rmic是JDK内的一个工具,用来为一个服务类产生stub和skeleton。rmic有一些选项可以调整,包括不要产生skeleton、查看源代码、甚至使用IIOP作为协议。
- 大小: 24.6 KB
- 大小: 19.2 KB
- 大小: 27.5 KB
分享到:
相关推荐
java rmi java rmijava rmi javajava rmi java rmi rmi
java RMI技术实现的网络聊天室 编译通过,很完整的。代码很有参考价值
采用JAVA rmi,带图形界面,完全由自己实现的聊天室,具备基本的聊天功能,可以自己扩充功能
检测javaRMI反序列化漏洞
java RMI
java RMI实现代码。分为客户端和服务器端,有清楚的代码注释。
Java RMI 简单示例
在这次的项目中,对于客户端与服务器之间的通信,想了许多办法,由于做的是富客户端应用,最终将技术选定在了RMI和Java-sockets两种之间,其中RMI的灵活性不高,客户端和服务器端都必须是java编写,但使用比较方便,...
JavaRMI.pdf
最近在学习代理模式,用到了java rmi远程调用,包含服务端和客户端,之前一直没有接触过,学习了java rmi远程调用,一方面可以了解代理模式,一方面熟悉java低层的远程
《Java RMI》一书的英文版本,With Java RMI, you'll learn tips and tricks for making your RMI code excel. This book provides strategies for working with serialization, threading, the RMI registry, ...
Java编程rmi实例,给出远程方法调用技术在java方面的具体例子。
javaRMI完整版.pdf
Java RMI的应用——学习RMI的简单编程应用。编写一个课程成绩管理程序,要求用Java RMI实现
Java RMI实例
我的博客《Java中的RMI(远程方法调用)》的示例代码
这是本人搜集整理的Java RMI规范,中文版,经过排版 共包括10个章节,2个附录
这是原创的最简单的Java RMI入门项目,内含二个Eclipse项目,一是服务器端,二是客户端。非常简单,只看其中的注释就能理解(当然先要知道什么是RMI了),只供入门用。 这是用Java 1.7编辑的,如果你用的版本低,则...
java 有关rmi进行分布式学习的参考文档
JAVARMI实例[文].pdf