`
huxiaojun_198213
  • 浏览: 101167 次
  • 性别: Icon_minigender_1
  • 来自: 深圳
社区版块
存档分类
最新评论

RMI规范--第三章

    博客分类:
  • RMI
阅读更多
主题:

Stub 与 skeleton

远程方法调用中的线程使用

远程对象的垃圾收集

动态类的加载

通过代理服务器透过防火墙的 RMI

3.1 Stub 与 skeleton

在与远程对象的通信过程中,RMI 将使用标准机制(用于 RPC 系统):stubs与 skeletons。远程对象的stub担当远程对象的客户本地代表或代理人角色。

调用程序将调用本地stub的方法,而本地stub将负责执行对远程对象的方法调用。在RMI中,远程对象的stub与该远程对象所实现的远程接口集相同。

当stub的方法被调用时,将执行下列操作:

1).初始化与包含远程对象的远程虚拟机的连接。

2).对远程虚拟机的参数进行编组(写入并传输)

3).等待方法调用结果

4).解组(读取)返回值或返回的异常

5).将值返给调用者

为向调用程序展示比较简单的调用机制,stub 将参数的序列化和网络级通信隐藏了起来。

在远程虚拟机中,每个远程对象都可以有相应的 skeleton(纯 JDK1.2 环境中不需要 skeleton)。skeleton 负责将调用分配给实际的远程对象实现。

当一个skeleton接收到方法调用时,它执行以下操作:

1).解编(读取)远程方法的参数

2).调用实际远程对象实现上的方法将结果(返回值或异常)编组(写入并传输)给调用程序


由于JDK1.2,v1.2中引入了额外的stub协议,使得在此平台中可以不再需要skeletons.

相反,在JDK1.1,需要使用通用代码来完成skeleton的职责。stub 和 skeleton可以通过rmic 编译器生成。


3.2 远程方法调用中的线程使用

RMI运行时分配给远程对象实现的方法可能在也可能不在独立的线程中执行。

RMI 运行时将无法担保远程对象与线程的映射关系。因为同一个远程对象的远程方法调用可能会同时执行,所以远程对象实现需确保其实现是线程安全的。

3.3 远程对象的垃圾收集

与在本地系统中相同,在分布式系统中自动删除那些不再被任何客户机引用的远程对象是令人满意的。

这可以将程序员从跟踪远程对象客户机以便适时终止的任务中解脱出来。

RMI 使用与 Modula-3 网络对象相似的引用计数的垃圾收集算法

  要实现引用计数垃圾收集,RMI 运行时需要跟踪每个 Java 虚拟机内的所有活动引用。当活动引用进入 Java 虚拟机时,其引用计数将加 1。

首次引用某对象时会向该对象的服务器发送“referenced”消息。当发现活动引用在本地虚拟机中并未被引用时,该数将减 1。

放弃最后的引用时,未被引用的消息将被发送到服务器。

协议中存在很多微妙之处,其中大部分都与维护引用或未引用消息的次序有关,以确保对象不被过早地收集。

当某远程对象不被任何客户机所引用时,RMI运行时将对其进行弱引用。如果不存在该对象的其它本地引用,则弱引用将允许 Java 虚拟机的垃圾收集器放弃该对象。

通过保持对对象的常规引用或弱引用,分布式垃圾收集算法可与本地 Java 虚拟机的垃圾收集器以常规方式进行交互。

只要存在对远程对象的本地引用,就不能将远程对象当作垃圾进行收集,而且该远程对象也可在远程调用中传送或返回客户机。

传递远程对象也将同时把目标虚拟机的标识符添加到被引用集中。

需要未引用通知的远程对象必须实现java.rmi.server.Unreferenced 接口。当这些引用不再存在时,将调用unreferenced 方法。当发现引用集为空时,也将调用 unreferenced。因此,unreferenced 方法可能会被多次调用。

只有当没有本地和远程引用时,才可收集远程对象。

注意,如果在客户机和远程服务器对象之间存在网络分区,则可能会过早地收集、远程对象(因为传输可能认为客户机已失效)。

由于可能会出现过早收集的现象,因此远程引用将不能保证引用的完整性。换句话说,远程引用实际上可能指向不存在的对象。使用此类引用时将抛出必须由应用程序处理的 RemoteException。


3.4 动态类加载

RMI 允许在RMI调用中,传递参数、返回值和异常或任何可序列化对象。

RMI 使用对象序列化机制将数据从一个虚拟机传输到另一个虚拟机,同时用相应的位置信息注释调用流,以便在接收端上加载类定义文件。

当解编远程方法调用的参数和返回值以使之成为接收虚拟机中的有效对象时,流中所有类型的对象都需要类定义。

解编过程将首先尝试通过本地类加载上下文(当前线程的上下文类加载器)中的名称来解析类。

RMI 也提供动态加载作为参数和返回值传送的实际对象类型的类定义的手段(其中远程方法调用的参数和返回值来自传送终点所指定的网络位置)。

这包括远程 stub 类的动态下载 - 该类对应于特定远程对象实现类(用于包含远程引用)及 RMI 调用中通过值传送的任何其它类型,例如在解编端的类加载上下文中尚不可用的,声明参数类型的子类。

为了支持动态类加载,RMI 运行时使用用于编组、解编 RMI 参数和返回值的编组流的特定 java.io.ObjectOutputStream 和 java.io.ObjectInputStream子类。

这些子类覆盖了 ObjectOutputStream 的 annotateClass 方法和ObjectInputStream 的 resolveClass 方法,以便就何处定位包含对应于流中类描述符的类定义的类文件交换信息。


对于每个写入 RMI 编组流的类描述符,annotateClass 方法将把类对象调用java.rmi.server.RMIClassLoader.getClassAnnotation 的结果添加到流中。

该结果可能为空,也可能是表示 codebase URL 路径(以空格分隔的 URL 列表)的 String 对象。利用该 codebase URL 路径,远程终点可下载所给类的定义文件。


对于从 RMI 编组流中读取的每个类描述符,resolveClass 方法将从流中读取单个对象。如果该对象是 String(且 java.rmi.server.useCodebaseOnly

属性不是 true),则 resolveClass 将返回调用 RMIClassLoader.loadClass的结果,并以所注解的 String 对象作为第一个参数,以类描述符中所需类名作为第二个参数。

否则,resolveClass 将返回调用 RMIClassLoader.loadClass的结果,并以所需的类名作为唯一参数。

有关 RMI 中类加载的详细信息,参见“RMIClassLoader 类”(5.6)一节。


3.5 通过代理服务器透过防火墙的 RMI

RMI 传输层通常试图将直接套接字在Internet的主机上打开。然而,许多Intranet 的防火墙不允许这样做。

因此,缺省 RMI 传输提供两种基于 HTTP 的机制,可使防火墙后的客户机调用驻留在防火墙外的远程对象方法。

3.5.1 如何将 RMI 调用包装在 HTTP 协议内

要透过防火墙,传输层可在防火墙信任的 HTTP 协议范围内嵌入 RMI 调用。

将RMI调用数据作为 HTTP POST 请求的主体发送出去后,反馈信息将返回到HTTP响应主体内。

传输层可通过以下两种方法构造 POST 请求:

1. 如果防火墙代理服务器可以把 HTTP 请求定向到主机的任意端口,HTTP请求就会被直接转发到 RMI 服务器正在监听的端口上。
目标计算机上的缺省RMI传输层可通过能识别并解码 POST 请求内的 RMI 调用的服务器套接字进行监听。

2. 如果防火墙代理服务器只能把 HTTP 请求定向到某个已知的 HTTP 端口,该调用就会被转发到正在主机端口 80 上监听的 HTTP 服务器,而且将执行 CGI
脚本以转发对同一计算机上目标 RMI 服务器端口的调用。

3.5.2 缺省套接字工厂

RMI传输实现(包括对java.rmi.server.RMISocketFactory的扩展),是用来为客户端和服务器端sockets发送和接收RMI调用的默认资源提供者。

此默认socket factory可以通过java.rmi.server.RMISocketFactory.getDefaultSocketFactory方法获取。

该缺省套接字工厂可创建套接字以透明地提供防火墙通道机制,如下所示:

1).客户机套接字将自动尝试与无法用直接套接字联系的主机进行 HTTP 连接。

2).服务端socket自动发现如果新来的连接是一个HTTP POST请求的话,将会返回一个HTTP响应。

工厂的 java.rmi.server.RMISocketFactory.createSocket 方法将提供带有此缺省行为的客户机端套接字。工厂的

java.rmi.server.RMISocketFactory.createServerSocket方法将提供带有此缺省行为的服务器端套接字。

3.5.3 配置客户机

无需特别配置即可使客户机透过防火墙发送 RMI 调用。但如果将 java.rmi.server.disableHttp 属性的布尔值设置为“true”,客户机即可禁止将 RMI 调用包装为 HTTP 请求。

3.5.4 配置服务器

------------------------------------------------------------------
注意 - 主机名不应为主机的 IP 地址,因为某些防火墙代理服务器不传送这种主机名。
------------------------------------------------------------

1. 为了使服务器主机域外的客户机能够调用服务器远程对象的方法,客户机必须找到该服务器。为此,服务器导出的远程引用必须包含服务器主机的全名。

本信息可否应用于运行服务器的 Java 虚拟机,取决于服务器平台和网络环境。如果不可用,则启动服务器时必须通过 java.rmi.server.hostname 属性指定主机的全名。

例如,在 chatsubo.javasoft.com上的主机,可以用以下命令启动 RMI 服务器类ServerImpl:

java -Djava.rmi.server.hostname=chatsubo.javasoft.com ServerImpl

2. 如果服务器不支持防火墙后可传送到随意端口的 RMI 客户机,则可使用如下配置:

1. HTTP 服务器在端口 80 上监听。

2. CGI 脚本的位置为别名 URL 路径

/cgi-bin/java-rmi.cgi

该脚本:
- 调用本地 Java 解释程序以执行可将请求传送到适当 RMI 服务器端口的传输层内部类。

- 在 Java 虚拟机中,以与 CGI 1.0 环境变量相同的名称和值定义属性。

用于 Solaris 和 Windows 32 操作系统的 RMI 分布式版本中提供了示例脚本。注意,脚本必须指定服务器上 Java 解释程序的完整路径。

3.5.5 性能问题与局限

在不考虑代理服务器传送延迟的情况下,由 HTTP 请求传送调用至少要比通过直接套接字传送慢一个数量级。

因为透过防火墙只能在一个方向初始化 HTTP 请求,同时防火墙外的主机也无法回调客户机的方法调用,所以客户机无法将其自身的远程对象导到防火墙以外。  
分享到:
评论

相关推荐

    Java Android 企业级编码规范

    #### 第3章 类的编写规则 - **命名规则**: - 所有包、类、接口、方法、属性、变量和参数都应使用英文命名,遵循一定的命名规范,如PascalCase和camelCase。 - 命名应尽可能反映其功能和用途,避免使用生僻或不...

    TongWeb5.0快速使用手册

    #### 第3章 liferay在TongWeb5.0上部署 - 该章节详细介绍了如何在TongWeb5.0平台上部署liferay应用,包括但不限于应用包准备、数据库导入、配置调整、具体部署步骤及后期测试等。 - 针对liferay的特殊配置需求进行了...

    第15章 复习的重点和内容课件

    本复习资料主要针对第15章的内容,涵盖了分布式程序设计的期末考试重点,主要包括Java EE的基本概念和体系结构、JSF开发以及EJB应用的基础知识。复习内容详细列举了可能出现在考试中的题型,如判断题、选择题、填空...

    JMX1.4 规范 翻译 第一章(介绍)(至1.6节)

    Java Management Extensions(JMX)1.4规范是Java平台中用于管理系统和应用程序的重要技术。它提供了管理和监控Java应用程序、设备和服务的标准框架。本章节主要介绍了JMX的基本概念、架构以及核心组件。 ### 1. ...

    JAVA编程技术教学大纲.

    ### 第3章 类与对象 - **内容概览**:深入讲解类、对象的创建与管理、修饰符、继承、多态、接口等核心概念。 - **教学要求**:学生需理解并掌握类、修饰符、多态和接口的应用。 - **重点与难点**:重点在于类、修饰...

    JSP高级编程(全)

    第3 章 EJB 技术进阶 3.1 实体EJB 的开发技术之一CMP EJB 3.2 实体EJB 的开发技术之二——BMP EJB 3.3 EJB 开发实例封装数据源 3.4 本章小结 第4 章 JSP 与J2EE 分布式处理技术 4.1 J2EE 和分布式处理技术 4.2 远程...

    Java网络高级编程

    第3章讨论了Java与CORBA(公共对象请求代理体系结构)不同体系的组件间通信技术。CORBA是一种跨平台、多语言的分布式对象总线规范,它允许不同语言编写的应用程序进行交互。 第4章介绍了Javabean技术,Javabean是...

    经典JAVA.EE企业应用实战.基于WEBLOGIC_JBOSS的JSF_EJB3_JPA整合开发.pdf

    第3章 深入使用JSF 117 3.1 JSF事件机制 118 3.1.1 Java事件模型概述 118 3.1.2 Java事件模型示例 119 3.1.3 JSF事件模型 120 3.1.4 Action事件 122 3.1.5 值改变事件 125 3.1.6 生命周期事件 128 3.1.7 将监听器...

    JAVA EE课件第一章

    它提供了分布式、可移植构件的框架,并定义了标准API,如JSP、EJB、XML、JDBC和RMI-IIOP,使得开发时间缩短,应用的维护和扩展变得更加简单。 **J2EE概念** J2EE将企业应用系统划分为不同的层次,包括表示层(用户...

    Thinking in Java 中文第四版+习题答案

    第3章 控制程序流程 3.1 使用Java运算符 3.1.1 优先级 3.1.2 赋值 3.1.3 算术运算符 3.1.4 自动递增和递减 3.1.5 关系运算符 3.1.6 逻辑运算符 3.1.7 按位运算符 3.1.8 移位运算符 3.1.9 三元if-else运算符 3.1.10 ...

    中间件技术及应用考试复习重点

    #### 第三章 COM相关技术 ##### 一、COM概述 1. **COM定义**:组件对象模型(COM)是一种软件对象组件之间通信的标准,它提供了一种二进制和网络兼容的规范,允许组件之间进行通信,无论这些组件位于同一台计算机...

    java课堂笔记_自己总结的

    #### 第一章 SQL Server 基本操作 ##### SQL Server 操作须知 1. **安装路径**: 安装文件及其安装路径都不能包含中文字符,否则可能会导致安装失败或出现其他错误。 2. **版本有效期**: 如果安装后一段时间内能够...

    Think in Java(中文版)chm格式

    第3章 控制程序流程 3.1 使用Java运算符 3.1.1 优先级 3.1.2 赋值 3.1.3 算术运算符 3.1.4 自动递增和递减 3.1.5 关系运算符 3.1.6 逻辑运算符 3.1.7 按位运算符 3.1.8 移位运算符 3.1.9 三元if-else...

    JAVA_Thinking in Java(中文版 由yyc,spirit整理).chm

    第3章 控制程序流程 3.1 使用Java运算符 3.1.1 优先级 3.1.2 赋值 3.1.3 算术运算符 3.1.4 自动递增和递减 3.1.5 关系运算符 3.1.6 逻辑运算符 3.1.7 按位运算符 3.1.8 移位运算符 3.1.9 三元if-else运算符 3.1.10 ...

    Thinking in Java(中文版 由yyc,spirit整理).chm

    第3章 控制程序流程 3.1 使用Java运算符 3.1.1 优先级 3.1.2 赋值 3.1.3 算术运算符 3.1.4 自动递增和递减 3.1.5 关系运算符 3.1.6 逻辑运算符 3.1.7 按位运算符 3.1.8 移位运算符 3.1.9 三元if-else运算符 3.1.10 ...

    Java初学者入门教学

    第3章 控制程序流程 3.1 使用Java运算符 3.1.1 优先级 3.1.2 赋值 3.1.3 算术运算符 3.1.4 自动递增和递减 3.1.5 关系运算符 3.1.6 逻辑运算符 3.1.7 按位运算符 3.1.8 移位运算符 3.1.9 三元if-else运算符 3.1.10 ...

    JAVA_Thinking in Java

    第3章 控制程序流程 3.1 使用Java运算符 3.1.1 优先级 3.1.2 赋值 3.1.3 算术运算符 3.1.4 自动递增和递减 3.1.5 关系运算符 3.1.6 逻辑运算符 3.1.7 按位运算符 3.1.8 移位运算符 3.1.9 三元if-else运算符 3.1.10 ...

    ThinkInJava

    第3章 控制程序流程 3.1 使用Java运算符 3.1.1 优先级 3.1.2 赋值 3.1.3 算术运算符 3.1.4 自动递增和递减 3.1.5 关系运算符 3.1.6 逻辑运算符 3.1.7 按位运算符 3.1.8 移位运算符 3.1.9 三元if-else运算符 3.1.10 ...

Global site tag (gtag.js) - Google Analytics