Hadoop中的RPC應用實例
RPC概述
RPC是指遠程過程調用,也就是說兩臺不同的服務器(不受操作系統限制),一個應用部署在Linux-A上,一個應用部署在Windows-B或Linux-B上,若A想要調用B上的某個方法method(),由於不在一個內存空間,不能直接調用,需要通過網絡來表達調用的語意和傳達調用的參數。
在接觸RPC之前,用得最多的莫過於WebService。WebService可以說是在RPC發展的基礎之上。RPC的協議有很多,比如最早的CORBA,Java RMI,Web Service等,又比如現在阿裏巴巴的Dubbo,Apache下的hadoop項目。該篇樓主主要以hadoop的RPC為例。
hadoop為何要使用RPC?在HDFS中,我們通過jsp可查看到有DataNode,NameNode,SecondaryNameNode主要進程(樓主只啟動了HDFS),我們客戶端Client與NameNode通信,NameNode與DataNode的通信,都是在不同進程間,不同系統間的通信。
RPC流程
通過下圖,我們簡單分析RPC的執行流程:
首先,要解決通訊的問題,主要是通過在Client和Server之間建立TCP連接,遠程過程調用的所有交換的數據都在這個連接裏傳輸。連接可以是按需連接,調用結束後就斷掉,也可以是長連接,多個遠程過程調用共享同一個連接。
第二,要解決尋址的問題,也就是說,A服務器上的應用怎麽告訴底層的RPC框架,如何連接到B服務器(如主機或IP地址)以及特定的端口,方法的名稱名稱是什麽,這樣才能完成調用。
第三,當Client上的應用發起遠程過程調用時,方法的參數需要通過底層的網絡協議如TCP傳遞到Server,由於網絡協議是基於二進制的,內存中的參數的值要序列化成二進制的形式,也就是序列化(Serialize),通過尋址和傳輸將序列化的二進制發送給B服務器。
第四,Server收到請求後,需要對參數進行反序列化(序列化的逆操作),恢復為內存中的表達方式,然後找到對應的方法(尋址的一部分)進行本地調用,然後得到返回值。
一、環境準備:
CentOS 6.9 32位
Linux和Windows版的Eclipse 32位
Hadoop 2.4.1版本
JDK 7+
二、Linux和Windows中的都需要引入Hadoop的Jar包:創建一個 User Libraries,引入
三、Linux中Eclipse作為服務端
- 1、創建一個接口LoginServiceInterface.java
package cn.joker.hadoop.rpc; public interface LoginServiceInterface { public static final long versionID=1L; public String login(String username,String password); }
- 2、創建一個接口實現類LoginServiceImpl.java
package cn.joker.hadoop.rpc; public class LoginServiceImpl implements LoginServiceInterface { @Override public String login(String username, String password) { // TODO Auto-generated method stub return username + " logged in successfully!"; } }
- 3、創建一個啟動類Starter.java
package cn.joker.hadoop.rpc; import java.io.IOException; import org.apache.hadoop.HadoopIllegalArgumentException; import org.apache.hadoop.conf.Configuration; import org.apache.hadoop.ipc.RPC; import org.apache.hadoop.ipc.RPC.Builder; import org.apache.hadoop.ipc.Server; public class Starter { public static void main(String[] args) throws HadoopIllegalArgumentException, IOException { Builder builder = new RPC.Builder(new Configuration()); builder.setBindAddress("weekend110").setPort(10000).setProtocol(LoginServiceInterface.class).setInstance(new LoginServiceImpl()); Server server = builder.build(); server.start(); } }
四、Windows中的Eclipse作為客戶端:
- 1、創建一個接口LoginServiceInterface.java
package cn.joker.hadoop.rpc; public interface LoginServiceInterface { public static final long versionID=1L; public String login(String username,String password); }
- 2、創建一個控制類LoginController.java
package cn.joker.hadoop.rpc; import java.net.InetSocketAddress; import org.apache.hadoop.conf.Configuration; import org.apache.hadoop.ipc.RPC; public class LoginController { public static void main(String[] args) throws Exception { LoginServiceInterface proxy = RPC.getProxy(LoginServiceInterface.class, 1L, new InetSocketAddress("weekend110", 10000), new Configuration()); String result = proxy.login("kevintan", "abc1234"); System.out.println(result); } }
五、運行Linux端的服務,再運行Windows端的請求,即可完成一個簡單的RPC應用。
Hadoop中的RPC應用實例