目的:

  通过本文,可以加深对Java RMI的理解,知道它的工作原理,怎么使用等. 也为了加深我自己的理解,故整理成文.不足之处,还望指出.

概念解释:

RMI(RemoteMethodInvocation):远程方法调用,顾名思义,通过远程的方式调用非本地对象的方法并返回结果。使用远程调用通常解决本地计算瓶颈问题,例如分布式记算,最近很火的阿尔法狗人机大战,据说运算使用上千个CPU。

JRMP(java remote method protocol):java远程方法协议,这是完成java到java远程调用的协议,基于TCP协议。

stub与skeleton:这两个概念下面会用到,这里解释下,skeleton是放在服务端的代理,它知道真正的对象在哪。stub是放在客户端的代理,它记录了查找和调用skeleton信息。理解成远程对象引用也成.

容易混淆的概念:

  远程方法调用与远程过程调用的区别:远程方法调用是java独有的,基于JRMP对象流协议实现,支持传输java序列化对象。远程过程调用是基于socket技术实现的,不能传输java对象,socket套接字协议支持多种语言。它们都是基于TCP协议传输。远程方法调用传输的是java序列化对象和基本数据类型,而远程过程调用不支持传输对象。

RMI调用模型:

从宏观看,想要远程调用需要做两件事情,1,服务端向本地对象注册表中注册能被调用的远程对象. 2,客户端向远程对象注册表请求远程对象的引用.

Java中RMI实现:

先通过一个例子了解Java中RMI是怎么用的,然后再根据代码分析源码是如何实现的.

1,先创建远程对象接口,继承自Remote(稍后源码中有分析为什么要有这个接口)

package remote.test;import java.rmi.Remote;
import java.rmi.RemoteException;
/*** 远程接口,实现Remote* @author lxz**/
public interface IRemote extends Remote{public String show()throws RemoteException;//声明方法
}

2,接口实现,需要继承UnicastRemoteObject类,等会分析

package remote.test;import java.rmi.RemoteException;
import java.rmi.server.UnicastRemoteObject;/*** 远程接口实现,继承UnicastRemoteObject* @author lxz**/
public class RemoteImpl extends UnicastRemoteObject  implements IRemote{public RemoteImpl()throws RemoteException{}//构造方法public String show()throws RemoteException{//调用方法实现System.out.println("进入");System.out.println(this.toString());return "远程调用成功";}
}

3,服务端向本地端口1234对象注册表注册对象和它的名字

package remote.test;import java.net.MalformedURLException;
import java.rmi.AlreadyBoundException;
import java.rmi.RemoteException;
import java.rmi.registry.LocateRegistry;
import java.rmi.registry.Registry;/***  服务端启动,创建端口上的对象注册列表,向对象注册表中注册远程调用对象* @author lxz**/
public class TestServer {public static void main(String[] args) throws MalformedURLException, RemoteException, AlreadyBoundException, InterruptedException {RemoteImpl r = new RemoteImpl();//创建远程对象Registry rr = LocateRegistry.createRegistry(1234); //创建1234端口上的对象注册表,如果已经创建了就用getRegistry方法获取rr.bind("testrmi", r);//向注册表中注册对象System.out.println(r.toString());}
}    

4,根据JDK API,以上远程服务就算搭建完毕了,下面通过客户端调用测试

package remote.test;import java.net.MalformedURLException;
import java.rmi.Naming;
import java.rmi.NotBoundException;
import java.rmi.RemoteException;/*** 客户端启动,获得远程的对象注册表中的对象引用* @author lxz**/
public class TestClient {public static void main(String[] args) throws MalformedURLException, RemoteException, NotBoundException {IRemote r = (IRemote) Naming.lookup("rmi://localhost:1234/testrmi");//获取远程1234端口对象注册表中testrmi的stubString a = r.show();//调用引用的方法,实际上调用的是stub,由stub与服务端交互并返回结果System.out.println(a);}
}

执行结果如下:

------------------------------------------

服务端:

RemoteImpl[UnicastServerRef [liveRef: [endpoint:[192.168.1.253:58169](local),objID:[-60651394:1539d5944e6:-7fff, -6910034932968554489]]]]
客户端:

远程调用成功
------------------------------------------

这样就完成了一个远程对象注册与远程对象方法调用的完整例子. 现在根据这个例子来分析它为什么要继承UnicastRemoteObject,实现Remote,向注册表注册等等.

首先远程对象实现类中需要继承UnicastRemoteObject类,UnicastRemoteObject具有注册为远程对象,生成远程引用的功能等,所有都已经被JDK封装好了,不需要编写,其中的实现有些是sun包开头的,不公开.

UnicastRemoteObject继承关系:

有了远程对象实现类,看服务端的启动逻辑,其中:

Registry rr = LocateRegistry.createRegistry(1234); 

LocateRegistry类:用于创建或获取某端口的对象注册表

LocateRegistry.createRegistry:这个方法表示获得远程对象注册表引用,返回Registry对象

Registry:真正操作远程对象注册表的接口

接着,

rr.bind("testrmi", r);

利用Registry的对象,把刚刚创建的远程对象注册为名称testrmi. 这里还有一种写法,效果是一样的.

LocateRegistry.createRegistry(1234); //创建,如果已经创建了就可省略这一句
Naming.bind("rmi://localhost:1234/testrmi", r);//需要带上端口

Naming:与对象注册表交互的工具类

上面是服务端从远程对象创建到对象注册的整个逻辑.客户端调用的逻辑比较简单,先通过Naming工具类获取到远程对象的引用以后,就可以正常使用了

(IRemote) Naming.lookup("rmi://localhost:1234/testrmi");

这里返回的"引用"和通常讲的对象引用不同,是远程对象的引用信息.拿到这个"引用"以后就可以像使用真正的对象一样调用其中的方法.

结束.

http://www.cnblogs.com/qinggege/p/5306852.html

Java RMI(远程方法调用) 实例与分析 (转)相关推荐

  1. Java RMI远程方法调用详解

    Java RMI远程方法调用详解     [尊重原创,转载请注明出处]http://blog.csdn.net/guyuealian/article/details/51992182 一.Java R ...

  2. (转)Java RMI远程方法调用详解

    Java RMI远程方法调用详解 [尊重原创,转载请注明出处]http://blog.csdn.net/guyuealian/article/details/51992182 一.Java RMI机制 ...

  3. Java RMI远程方法调用学习总结

    RMI开发步骤总结如下: 1.声明的实体对象需要进行远程传输,需要继承Serializable. 2.创建远程接口及声明远程方法,需要继承Remote. 3.实现远程接口及远程方法,需要继承Unica ...

  4. Java RMI服务远程方法调用漏洞

    JAVA RMI 反序列化远程命令执行漏洞 漏洞资料 背景 原理 Payload构造 搭建本地测试环境 开启包含第三方库的RMI服务 测试RMI客户端 攻击测试 升级版攻击 Weblogic Comm ...

  5. Java RMI 框架(远程方法调用)

    RMI(即Remote Method Invoke 远程方法调用).在Java中,只要一个类extends了java.rmi.Remote接口,即可成为存在于服务器端的远程对象,供客户端访问并提供一定 ...

  6. java rmi 入门实例

    java rmi 入门实例 (2009-06-16 16:07:55) 转载▼ 标签: java rmi 杂谈 分类: java-基础  java rmi即java远程接口调用,实现了2台虚拟机之间的 ...

  7. java rmi 例子_RMI最简单的一个实例

    RMI最简单的一个实例 2008年06月21日 星期六 下午 07:30 1.    RMI最简单的一个实例,思路是你在服务器端创建一个方法addData(),该方法实现两个整数的相加,然从客户端远程 ...

  8. JAVA RMI简介与优缺点分析

    RMI方式的调用,如:rmi://10.20.134.140:2099/DataServer 1.Java RMI 简介 RMI(Remote Method Invocation),RMI是分布式对象 ...

  9. Java RMI学习与解读(二)

    写在前面# 接上篇文章,这篇主要是跟着看下整个RMI过程中的源码并对其做简单的分析 RMI源码分析# 还是先回顾下RMI流程: 创建远程对象接口(RemoteInterface) 创建远程对象类(Re ...

最新文章

  1. POJ 3414 Pots【广搜】
  2. iphone双卡_内部消息:iPhone 12不支持双卡5G,但国行问题不大|iphone|国行|手机|高通|骁龙...
  3. 文献引用的标准格式_论文参考文献格式标准~建议收藏
  4. Laravel新建对象的方法:make resolve 辅助函数app()
  5. java客户端作为kafka消费者测试
  6. git clone时出现gnutls_handshake() failed: The TLS connection was non-properly terminated.
  7. NOI图论算法:网络流
  8. LPI 认证考试介绍
  9. DeepMind科学家:强化学习足以满足通用AI需求
  10. jdk下载--操作系统
  11. JDK-Logger
  12. 批量修改mac系统文件的可读写权限
  13. 关于一直卡死的两段代码,望对LDD3有兴趣者戳开这个blog : )
  14. 计算机上什么盘放大型游戏好,大型游戏可以直接装到移动硬盘里玩吗?
  15. syscall 系统调用陷入_MIPS中的异常处理和系统调用【转】-阿里云开发者社区
  16. python开发贴吧_python爬虫-贴吧
  17. 1000并发的系统服务器配置,1000并发服务器配置
  18. android 显示大屏幕_android android如何将优化的体验带到大屏幕
  19. Eclipse设置护眼(绿豆沙)颜色
  20. 3d打印材料有哪几种

热门文章

  1. 使用VC++ 显示一首诗歌
  2. 图解netstat命令实例
  3. 图解Java 开发教程
  4. [Xcode 实际操作]六、媒体与动画-(3)使用CoreImage框架设置图片的单色效果
  5. ACID、数据库隔离级别
  6. iOS 开发一定要尝试的 Texture(ASDK)
  7. *Codeforces587E. Duff as a Queen
  8. WPF(C#)与MATLAB混合编程
  9. 截图工具当前未在计算机运行
  10. 【Linux学习】Linux系统管理2—作业调度