RMI开发 Step By Step
2010-02-22 11:02
274 查看
RMI(Remote Method Invocation)RMI是分布式对象软件包,它简化了在多台计算机上的JAVA应用之间的通信。RMI从JDK1.1以后开始支持。
RMI系统采用类似CORBA的对象请求代理机制,桩(Stub)是远程对象在客户端的代理,客户程序中的远程对象引用其实是对本地脏的引用。桩负责将远程调用请求通过远程引用层和传输层转发给服务端的框架(skeleton),再由框架将请求分派给服务程序中的对象实现。
远程引用层分为客户端与服务端两个相互协作的组件,负责完成远程调用的语义。
传输层也分为客户端与服务器两部分,负责建立与管理连接,跟踪远程对象,以及将调用请求分派给合适的对象实现实例。在服务端,传输层将调用请求向上转发给远程引用层,远程引用层作相应处理后转发给框架,由框架向上调用服务程序中的对象实现,对象实现执行真正的方法调用任务。远程调用返回结果送回客户程序的路线与调用请求的传送路线刚好相反,首先经过服务端的框架、远程引用层和传输层,再向上经过客户端的传输层、远程引用层和桩。
RMI体系结构图
![](http://hi.csdn.net/attachment/201002/22/2419231_1266854047u7g8.gif)
RMI在桩/框架层利用了两种关键技术。一种是java语言志用的对象串行化(object serialization)技术,该技术支持将对象的类型与值信息转为平坦的字节流形式,并可利用这种串行化表示重建与原对象状态相同的同类型对象,从而实现对象状态的持久性或网络传输,桩和框架利用这一技术对远程调用的参数与返回值进行打包与解包。另一种技术是动态类装载(dynamic class loading),用于在程序动态远行时装载客户程序所需的框,并支持java语言内建的类型检查与类型转换机制。
第一步,定义接口,继承java.rmi.Remote
程序代码
package zizz.rmi;
/**
* 定义一个问候者的接口.
* @author ZIZZ
* @Company manbuchina
* Create-Time:2007-8-16 下午11:06:48
*/
public interface Greeter extends java.rmi.Remote{
String greetByName(String name) throws java.rmi.RemoteException;
}
第二步,定义实现,继承UnicastRemoteObject
程序代码
package zizz.rmi;
import java.rmi.RemoteException;
import java.rmi.server.UnicastRemoteObject;
/**
* 问候者的实现.
* @author ZIZZ
* @Company manbuchina
* Create-Time:2007-8-16 下午11:08:46
*/
public class GreeterImpl extends UnicastRemoteObject implements Greeter {
/**
* serialVersionUID
*/
private static final long serialVersionUID = -5870885426008943753L;
/**
*
* @throws RemoteException
*/
public GreeterImpl() throws RemoteException {
//继承了UnicastRemoteObject,必须实现相应的构造器
super();
}
public String greetByName(String name) throws RemoteException {
return "您好," + name;
}
}
第三步,开发服务器端
程序代码
package zizz.rmi;
import java.net.MalformedURLException;
import java.rmi.AlreadyBoundException;
import java.rmi.Naming;
import java.rmi.RemoteException;
/**
* 服务程序
* @author ZIZZ
* @Company manbuchina
* Create-Time:2007-8-16 下午11:10:54
*/
public class GreeterServer {
public static void main(String[] args){
try {
GreeterImpl greeterImpl = new GreeterImpl();
//绑定服务对象
try {
Naming.bind("SayHello", greeterImpl);
} catch (AlreadyBoundException e) {
e.printStackTrace();
}
System.out.println("系统已经成功绑定服务对象.");
} catch (RemoteException e) {
System.out.println("错误信息为:" + e.getMessage());
e.printStackTrace();
} catch (MalformedURLException e) {
System.out.println("错误信息为:" + e.getMessage());
e.printStackTrace();
}
}
}
第四步,使用rmic产生客户端桩
rmic zizz.rmi.GreeterImpl
使用rmic将会产生一个GreeterImpl_Stub.class的新文件
第五步,将产生的客户端桩及接口copy到客户端
将GreeterImpl_Stub.class,Greeter.class这两个文件,使用jar命令打个包,取名叫rmiclient.jar
命令如下:
jar cvf rmiclient.jar zizz/rmi/GreeterImpl_Stub.class zizz/rmi/Greeter.class
第六步,编写客户端
程序代码
package zizz.rmi;
import java.net.MalformedURLException;
import java.rmi.Naming;
import java.rmi.NotBoundException;
import java.rmi.RemoteException;
/**
* RMI客户端
* @author ZIZZ
* @Company manbuchina
* Create-Time:2007-8-16 下午11:25:29
*/
public class GreeterClient {
public static void main(String[] args){
try {
//如果是其它服务器,则查找 rmi://server_name/SayHello
Greeter greeter = (Greeter)Naming.lookup("rmi://127.0.0.1/SayHello");
System.out.println(greeter.greetByName("ZIZZ"));
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (RemoteException e) {
e.printStackTrace();
} catch (NotBoundException e) {
e.printStackTrace();
}
}
}
第七步,使用rmiregistry起用服务,监听1099端口
在命令行下打入rmiregistry,启用RMI注册表。
注意,运行该注册表必须进入工程的Classpath下,也就是说,跟第八步运行服务器端必须在同一个路径
第八步,启用服务器端,将服务对象绑定到rmigegistry当中
java zizz.rmi.GreeterServer
第九步,运行客户端,查看结果
java zizz.rmi.GreeterClient
其实RMI开发是非常简单的,关键就是要把原理搞清楚,把开发顺序搞清楚就可以了。如果返回的结果是一个对象,那该对象必须实现串行化接口,不然,程序在运行期间将会报错。
RMI系统采用类似CORBA的对象请求代理机制,桩(Stub)是远程对象在客户端的代理,客户程序中的远程对象引用其实是对本地脏的引用。桩负责将远程调用请求通过远程引用层和传输层转发给服务端的框架(skeleton),再由框架将请求分派给服务程序中的对象实现。
远程引用层分为客户端与服务端两个相互协作的组件,负责完成远程调用的语义。
传输层也分为客户端与服务器两部分,负责建立与管理连接,跟踪远程对象,以及将调用请求分派给合适的对象实现实例。在服务端,传输层将调用请求向上转发给远程引用层,远程引用层作相应处理后转发给框架,由框架向上调用服务程序中的对象实现,对象实现执行真正的方法调用任务。远程调用返回结果送回客户程序的路线与调用请求的传送路线刚好相反,首先经过服务端的框架、远程引用层和传输层,再向上经过客户端的传输层、远程引用层和桩。
RMI体系结构图
![](http://hi.csdn.net/attachment/201002/22/2419231_1266854047u7g8.gif)
RMI在桩/框架层利用了两种关键技术。一种是java语言志用的对象串行化(object serialization)技术,该技术支持将对象的类型与值信息转为平坦的字节流形式,并可利用这种串行化表示重建与原对象状态相同的同类型对象,从而实现对象状态的持久性或网络传输,桩和框架利用这一技术对远程调用的参数与返回值进行打包与解包。另一种技术是动态类装载(dynamic class loading),用于在程序动态远行时装载客户程序所需的框,并支持java语言内建的类型检查与类型转换机制。
第一步,定义接口,继承java.rmi.Remote
程序代码
package zizz.rmi;
/**
* 定义一个问候者的接口.
* @author ZIZZ
* @Company manbuchina
* Create-Time:2007-8-16 下午11:06:48
*/
public interface Greeter extends java.rmi.Remote{
String greetByName(String name) throws java.rmi.RemoteException;
}
第二步,定义实现,继承UnicastRemoteObject
程序代码
package zizz.rmi;
import java.rmi.RemoteException;
import java.rmi.server.UnicastRemoteObject;
/**
* 问候者的实现.
* @author ZIZZ
* @Company manbuchina
* Create-Time:2007-8-16 下午11:08:46
*/
public class GreeterImpl extends UnicastRemoteObject implements Greeter {
/**
* serialVersionUID
*/
private static final long serialVersionUID = -5870885426008943753L;
/**
*
* @throws RemoteException
*/
public GreeterImpl() throws RemoteException {
//继承了UnicastRemoteObject,必须实现相应的构造器
super();
}
public String greetByName(String name) throws RemoteException {
return "您好," + name;
}
}
第三步,开发服务器端
程序代码
package zizz.rmi;
import java.net.MalformedURLException;
import java.rmi.AlreadyBoundException;
import java.rmi.Naming;
import java.rmi.RemoteException;
/**
* 服务程序
* @author ZIZZ
* @Company manbuchina
* Create-Time:2007-8-16 下午11:10:54
*/
public class GreeterServer {
public static void main(String[] args){
try {
GreeterImpl greeterImpl = new GreeterImpl();
//绑定服务对象
try {
Naming.bind("SayHello", greeterImpl);
} catch (AlreadyBoundException e) {
e.printStackTrace();
}
System.out.println("系统已经成功绑定服务对象.");
} catch (RemoteException e) {
System.out.println("错误信息为:" + e.getMessage());
e.printStackTrace();
} catch (MalformedURLException e) {
System.out.println("错误信息为:" + e.getMessage());
e.printStackTrace();
}
}
}
第四步,使用rmic产生客户端桩
rmic zizz.rmi.GreeterImpl
使用rmic将会产生一个GreeterImpl_Stub.class的新文件
第五步,将产生的客户端桩及接口copy到客户端
将GreeterImpl_Stub.class,Greeter.class这两个文件,使用jar命令打个包,取名叫rmiclient.jar
命令如下:
jar cvf rmiclient.jar zizz/rmi/GreeterImpl_Stub.class zizz/rmi/Greeter.class
第六步,编写客户端
程序代码
package zizz.rmi;
import java.net.MalformedURLException;
import java.rmi.Naming;
import java.rmi.NotBoundException;
import java.rmi.RemoteException;
/**
* RMI客户端
* @author ZIZZ
* @Company manbuchina
* Create-Time:2007-8-16 下午11:25:29
*/
public class GreeterClient {
public static void main(String[] args){
try {
//如果是其它服务器,则查找 rmi://server_name/SayHello
Greeter greeter = (Greeter)Naming.lookup("rmi://127.0.0.1/SayHello");
System.out.println(greeter.greetByName("ZIZZ"));
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (RemoteException e) {
e.printStackTrace();
} catch (NotBoundException e) {
e.printStackTrace();
}
}
}
第七步,使用rmiregistry起用服务,监听1099端口
在命令行下打入rmiregistry,启用RMI注册表。
注意,运行该注册表必须进入工程的Classpath下,也就是说,跟第八步运行服务器端必须在同一个路径
第八步,启用服务器端,将服务对象绑定到rmigegistry当中
java zizz.rmi.GreeterServer
第九步,运行客户端,查看结果
java zizz.rmi.GreeterClient
其实RMI开发是非常简单的,关键就是要把原理搞清楚,把开发顺序搞清楚就可以了。如果返回的结果是一个对象,那该对象必须实现串行化接口,不然,程序在运行期间将会报错。
相关文章推荐
- OAF二次开发step by step(二)--二次开发的环境的配置
- OAF二次开发step by step(四)--OAF二次开发程序的部署
- ActionScript 3.0 Step By Step系列(四):来自面向对象开发之前的呐喊:“学会写可重用的代码”
- 用Apache AXIS 开发 Web Services Step By Step(1)
- Archie osgEarth Step By Step ⑤OsgEarth开发指南——使用osgearth API编程动态建立地图
- Step by step——WinX开发入门教程-5
- Step by Step WebMatrix网站开发之三:Razor语法之一
- Step by Step WebMatrix网站开发之二:使用WebMatrix(3)
- Visual Studio 2013开发 mini-filter driver step by step 获取可执行文件名称 - 实现process monitor的一个功能 (10)
- 魅族m8开发 step by step(3)(BasicControl)
- Step by Step WebMatrix网站开发之一:Webmatrix安装
- Step by Step WebMatrix网站开发之二:使用WebMatrix(1)
- 第一章 Hadoop2.x 应用开发step by step——大数据概述
- 【Azure Services Platform Step by Step-第8篇】开发部署Azure留言板
- OAF二次开发step by step(三)--对具体的BC4J对象的客户化
- Visual Studio 2013开发 mini-filter driver step by step (5) - 读写文件
- ActionScript 3.0 Step By Step系列(五):走在面向对象开发的路上,以类为基础去思考编程问题
- Visual Studio 2013开发 mini-filter driver step by step 获取文件读写内容(6)
- eclipse 使用axis2 wizards 开发部署webserver step by step
- 在ubuntu上开发php step by step(1)