1. 程式人生 > >RPC呼叫遠端服務

RPC呼叫遠端服務

RPC(Remote Procedure Call Protocol,遠端過程呼叫協議),可以使本機像呼叫本地類一樣呼叫遠端服務,只需要提供一個介面給呼叫端,就可以使用RPC工具類拿到遠端服務代理,進而呼叫遠端服務(釋出的RPC服務)。關於RPC的具體介紹可以參見知乎上的回答(https://www.zhihu.com/question/25536695),本文僅介紹怎麼使用Hadoop中的RPC工具類來實現RPC的遠端過程呼叫。

以下是遠端程式碼:

package sempp.lsl.hadoop.rpc;

/**
 * Remote interface 遠端服務介面設計
 * @author lsl
 */
public interface LoginServiceInterface {
    public static final long versionID=1L;

    public String login(String userName,String passWord);
}

package sempp.lsl.hadoop.rpc;

public class LoginServiceImpl implements LoginServiceInterface {
	/**
	 * Remote Procedure 遠端服務介面的具體實現
	 */
	public String login(String userName, String passWord) {
		return userName +" login success";
	}
}

package sempp.lsl.hadoop.rpc;

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;
/**
 * Starter of RPC service  服務啟動
 * @author lsl
 */
public class Starter {
	
	public static void main(String args[]) throws Exception{
		//The host sempplsl-01 has published a web service on port 1600
		Builder builder=new RPC.Builder(new Configuration());
		builder.setBindAddress("sempplsl-01").setPort(1600).setProtocol(LoginServiceInterface.class).setInstance(new LoginServiceImpl());
		Server server=builder.build();
		server.start();
	}
}

----------End----------

以下是原生代碼:

package sempp.lsl.hadoop.rpc;
/**
 * 僅需要將遠端介面類拷貝到本地,具體實現還是在遠端
 * @author lsl
 */
public interface LoginServiceInterface {
	
	public static final long versionID=1L; 
	public String login(String userName,String passWord);
	
}
package sempp.lsl.hadoop.rpc;

import java.io.IOException;
import java.net.InetSocketAddress;
import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.ipc.RPC;
/**
 * 呼叫遠端服務
 * @author lsl
 */
public class LoginController {

	public static void main(String[] args) throws IOException {
		// LoginServiceInterface 所在包應當與伺服器端所在包 包名一致 否則會報錯
		//拿到RPC代理   代理的為主機sempplsl-01 上1600埠釋出的RPC服務,可以利用這種代理機制將具體服務的實現從web服務中剝離出來單獨釋出為RPC服務,實現對服務細節的封裝,而使用端只需要拿到服務的代理就可以完全實現該服務
		LoginServiceInterface proxy=RPC.getProxy(LoginServiceInterface.class, 1L, new InetSocketAddress("sempplsl-01",1600), new Configuration());
		//呼叫遠端服務(方法的具體實現在遠端服務中)
		String result = proxy.login("lsljiayou", "111");
		System.out.println(result);
        RPC.stopProxy(proxy);
	}
}

----------End----------

需要注意一點,本地介面和遠端介面所屬包名需要保持一致,否則會報錯,具體錯誤資訊為:

Caused by: org.apache.hadoop.ipc.RemoteException(org.apache.hadoop.ipc.RpcServerException): Unknown protocol: sempp.lsl.hadoop.rpc1.LoginServiceInterface

可以看出錯誤原因是找不到這個包下的介面服務。