軟體包名稱
主要描述
軟體包 javax.management.remote.rmi 的描述
RMI 連線器是供 JMX Remote API 使用的一種連線器,後者使用 RMI 將客戶端請求傳輸到遠程 MBean 伺服器。此包定義了 RMI 連線器的用戶直接引用客戶端和伺服器方所需的類。它還定義了某些類,用戶雖然不經常直接引用這些類但還必須定義,主要是為 RMI 連線器的不同實現之間實現互操作。
RMI 連線器支持 RMI 的 jrmp 和 IIOP 傳輸方式。
與 JMX Remote API 中的多數連線器類似,RMI 連線器通常有一個地址,它是一個 JMXServiceURL。對於使用默認 RMI 傳輸方式 (JRMP) 的連線器,此地址的協定部分為 rmi;對於使用 RMI/IIOP 的連線器,地址的協定部分為 iiop。
RMI 連線器地址有兩種形式:
在 JNDI 形式 中,URL 指示查找連線器的 RMI stub 的位置。此 RMI stub 是一個類型為 RMIServer 的 Java 對象,它提供了對連線器伺服器的遠程訪問。使用這種地址形式,可從包含在 URL 中的外部目錄條目獲取 RMI stub。外部目錄是指可由 JNDI 識別的任何目錄,通常是 RMI 註冊表、LDAP 或 CORBA 命名服務 (COS Naming)。
在編碼形式 中,URL 直接包括了連線到連線器伺服器所需的信息。使用 RMI/JRMP 時,編碼形式是伺服器對象的序列化 RMI stub,它採用 BASE64 編碼,未嵌入換行。使用 RMI/IIOP 時,編碼形式是伺服器對象的 CORBA IOR。
以下內容更詳細地介紹了地址。
創建 RMI 連線器伺服器
創建 RMI 連線器伺服器的一般方法是為方法 JMXConnectorServerFactory.newJMXConnectorServer 提供一個 RMI 連線器地址。連線器伺服器要連線到的 MBean 伺服器可作為該方法的一個參數指定。或者,也可以將連線器伺服器註冊為該 MBean 伺服器中的 MBean。
還可以通過構造 RMIConnectorServer 的實例(顯式或使用 MBean 伺服器的 createMBean 方法)來創建 RMI 連線器伺服器。
選擇 RMI 傳輸方式
在創建連線器伺服器時,通過在 serviceURL 的 protocol 部分指定 rmi 或 iiop,您可以選擇 RMI 傳輸方式(JRMP 或 IIOP)。通過實例化 RMIServerImpl 的一個適當的子類並將其提供給 RMIConnectorServer 構造方法,您還可以創建特殊的連線器伺服器。
伺服器生成的連線器地址
如果您指定的 serviceURL 包含空 URL 路徑(在可選的主機和連線埠後),或者未指定 serviceURL,則連線器伺服器將創建一個可供客戶端連線使用的新 JMXServiceURL:
如果 serviceURL 如下所示:
service:jmx:rmi://host:port
則連線器伺服器將生成一個 RMIJRMPServerImpl,且返回如下所示的 JMXServiceURL:
service:jmx:rmi://host:port/stub/XXXX
其中,XXXX 為所生成對象的 stub 的序列化形式,其編碼採用 BASE64,不帶換行。
如果 serviceURL 如下所示:
service:jmx:iiop://host:port
則連線器伺服器將生成一個 RMIIIOPServerImpl ,且返回如下所示的 JMXServiceURL:
service:jmx:iiop://host:port/ior/IOR:XXXX
其中,IOR:XXXX 為所生成對象的互操作對象引用 (Interoperable Object Reference) 的標準 CORBA 編碼。
如果沒有 serviceURL,則必須有一個用戶提供的 RMIServerImpl。如果在此對象上調用 toStub 方法返回 Stub 的實例,則連線器伺服器將用上述的 iiop 形式生成 JMXServiceURL。否則,它將用 rmi 形式生成 JMXServiceURL。
用戶提供的 serviceURL 中的 host 為可選項。如果有這一項,則將其複製到生成的 JMXServiceURL 中,但是其他方面會忽略此項。如果沒有這一項,則生成的 JXMServiceURL 將包括本地主機名。
用戶提供的 serviceURL 中的 port 也是一個可選項。如果有這一項,則同樣將其複製到生成的 JMXServiceURL 中;否則,生成的 JMXServiceURL 不帶連線埠。對於使用 rmi 協定的 serviceURL,如果有 port,則它指示生成的遠程對象應在該連線埠上導出。它沒有任何其他作用。
如果用戶提供了 RMIServerImpl 而不是 JMXServiceURL,則生成的 JMXServiceURL 將在其 host 部分包含本地主機名並且不帶 port。
基於目錄條目的連線器地址
作為剛才介紹的生成地址的另外一種情況,創建連線器伺服器時提供的 serviceURL 地址指定的是目錄地址,其中可存儲提供的或生成的 RMIServer stub。然後客戶端和伺服器都可以使用此目錄地址。
這種情況下,serviceURL 具有如下兩種形式之一:
service:jmx:rmi://host:port/jndi/jndi-name
service:jmx:iiop://host:port/jndi/jndi-name
其中 jndi-name 是一個可提供給 javax.naming.InitialContext.bind 的字元串。
同樣,host 和 :port 均可忽略。
連線器伺服器將基於協定(rmi 或 iiop),對於 rmi,還包括 port(如果有)生成 RMIServerImpl。連線器伺服器啟動後,它將從此對象使用其 toStub 方法派生一個 stub 並使用給定的 jndi-name 保存該對象。同樣也要參考由 JNDI API 定義的屬性。
例如,假設 JMXServiceURL 為:
service:jmx:rmi://ignoredhost/jndi/rmi://myhost/Myname
則連線器伺服器將生成 RMIJRMPServerImpl 並使用該 JNDI 名稱保存其 stub
rmi://myhost/myname
它表示運行在主機 myhost 的默認連線埠上 RMI 註冊表中的 myname 項。注意,RMI 註冊表只允許從本地主機註冊。因此在這種情況下,myhost 必須是運行連線器伺服器的主機名。
在此 JMXServiceURL 中,第一個 rmi: 指定 RMI 連線器,第二個 rmi: 指定 RMI 註冊表。
另舉一個例子,如果 JMXServiceURL 為:
service:jmx:iiop://ignoredhost/jndi/ldap://dirhost:9999/cn=this,ou=that
則該連線器伺服器將生成 RMIIIOPServerImpl 並使用該 JNDI 名稱保存其 stub
ldap://dirhost:9999/cn=this,ou=that
它表示 LDAP 目錄中的 cn=this,ou=that 條目,該目錄在運行主機 dirhost 的連線埠 9999 上。
如果 JMXServiceURL 為:
service:jmx:iiop://ignoredhost/jndi/cn=this,ou=that
則該連線器伺服器將生成 RMIIIOPServerImpl 並使用該 JNDI 名稱保存其 stub
cn=this,ou=that
要在這種情況下正常工作,JNDI API 必須經過適當配置,以提供有關要使用的目錄的信息。
這些示例中,主機名 ignoredhost 未被連線器伺服器或其客戶端使用。可將其忽略,例如:
service:jmx:iiop:///jndi/cn=this,ou=that
但是,在連線器伺服器運行的主機上使用主機名是一個不錯的做法。這通常不同於目錄主機的名稱。
連線器伺服器的屬性
使用默認的 JRMP 傳輸方式時,可使用為 RMIConnectorServer 構造方法給定的 environment 中的 jmx.remote.rmi.client.socket.factory 和 jmx.remote.rmi.server.socket.factory 屬性指定 RMI 套接字工廠。這些屬性的值的類型必須分別為 RMIClientSocketFactory 和 RMIServerSocketFactory。這些工廠在創建與連線器關聯的 RMI 對象時使用。
創建 RMI 連線器客戶端
RMI 連線器客戶端通常使用 JMXConnectorFactory 且具有協定 rmi 或 iiop 的 JMXServiceURL 進行構造。
如果 JMXServiceURL 由伺服器生成,如上文中的“伺服器生成的連線器地址”所述,則客戶端將需要直接或間接地從伺服器獲取該值。通常情況下,伺服器將 JMXServiceURL 存儲在一個檔案或查找服務中以便使用。
如果 JMXServiceURL 使用目錄語法,如上文中的“基於目錄條目的連線器地址”所述,則客戶端可用剛剛介紹的方法獲取該值,或者客戶端和伺服器可能都知道要使用的適當目錄條目。例如,如果 Whatsit 代理的連線器伺服器使用主機 myhost 上 RMI 註冊表中的 whatsit-agent-connector 條目,則客戶端和伺服器都知道適當的 JMXServiceURL 為:
service:jmx:rmi:///jndi/rmi://myhost/whatsit-agent-connector
如果 RMI stub 的類型為 RMIServer,則可以使用 RMIConnector 的適當構造方法直接構造 RMI 連線。
為 RMI/IIOP 連線器指定一個 ORB
使用 IIOP 傳輸方式時,客戶端和伺服器可使用屬性 java.naming.corba.orb 指定要使用的 ORB。連線器伺服器連線到 ORB 的動作發生時間為 start,連線器客戶端連線到 ORB 的動作發生時間為 connect。如果 java.naming.corba.orb 屬性包含在環境 Map 中,則其值(一個 ORB)將用於連線 IIOP Stub。否則,將通過調用 org.omg.CORBA.ORB.init((String[])null,(Properties)null) 創建一個新的 org.omg.CORBA.ORB。位於同一 JVM 中的後續 RMI 連線器客戶端或伺服器可重用此 ORB,或者可用同樣的方式創建另一個 ORB。
如果指定了 java.naming.corba.orb 屬性但它並不指向一個 ORB,則將拋出 IllegalArgumentException。
當 IIOP 遠程對象(Stub 或 Server)在被傳入到 RMIConnector 和 RMIConnectorServer 之前通過手動創建和連線到 ORB 時,這裡描述的機制將不適用。
另請參見:
JavaTM Remote Method Invocation (RMI), Java Naming and Directory InterfaceTM (JNDI), RFC 2045, section 6.8, "Base64 Content-Transfer-Encoding"