废话不多说,直接上代码:
1. RpcServer:rpc服务端,用于启动Socket监听端口
import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
public class RpcServer {
// 监听端口
private int port = 8888;
// 自定义线程池,用于处理客户端请求
private static ThreadPoolExecutor threadPool = new ThreadPoolExecutor(5, 10, 3000L, TimeUnit.SECONDS, new ArrayBlockingQueue<>(100));
// 模拟spring 注入Bean容器
static Map<String, Object> beanContainer = new HashMap<>();
static {
beanContainer.put("helloService", new HelloServiceImpl());
}
public void start() {
ServerSocket ss = null;
try {
ss = new ServerSocket(port);
} catch (IOException e) {
e.printStackTrace();
}
while(true) {
try {
System.out.println("服务端启动成功,等待请求。。。");
Socket s = ss.accept();
threadPool.submit(new RpcServerHandler(s));
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
2. RpcServerHandler:处理客户端请求
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.lang.reflect.Method;
import java.net.Socket;
public class RpcServerHandler implements Runnable{
Socket s;
public RpcServerHandler(Socket s) {
this.s = s;
}
@Override
public void run() {
System.out.println("服务端开始处理请求");
ObjectInputStream ois = null;
ObjectOutputStream oos = null;
try {
ois = new ObjectInputStream(s.getInputStream());
// 获取接口名称
String serviceName = ois.readUTF();
// 获取目标方法名
String methodName = ois.readUTF();
// 具体的实现类beanName
String beanName = ois.readUTF();
// 使用反射调用目标方法
Class<?> c = Class.forName(serviceName);
Method m = c.getMethod(methodName);
Object result = m.invoke(RpcServer.beanContainer.get(beanName));
oos = new ObjectOutputStream(s.getOutputStream());
// 方法返回值返回客户端
oos.writeObject(result);
System.out.println("服务端处理请求成功");
} catch (Exception e) {
System.out.println("RpcHandler error: " + e.getMessage());
e.printStackTrace();
} finally {
if(null != ois) {
try {
ois.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if(null != oos) {
try {
oos.flush();
oos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
3. RpcClientProxy: 客户端接口代理类
import org.springframework.cglib.proxy.InvocationHandler;
import org.springframework.cglib.proxy.Proxy;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.lang.reflect.Method;
import java.net.Socket;
public class RpcClientProxy {
// 服务端IP
private final static String ipAddress = "localhost";
// 服务端端口
private final static int port = 4444;
/* 创建代理对象,在代理对象中使用Socket请求服务端获取数据 */
public static Object proxy(Class interfaces, String beanName) {
return Proxy.newProxyInstance(RpcClientProxy.class.getClassLoader(), new Class[]{interfaces}, new InvocationHandler() {
@Override
public Object invoke(Object o, Method method, Object[] objects) throws Throwable {
ObjectInputStream ois = null;
ObjectOutputStream oos = null;
try {
System.out.println("客户端开始请求数据");
Socket s = new Socket(ipAddress, port);
oos = new ObjectOutputStream(s.getOutputStream());
oos.writeUTF(interfaces.getName());
oos.writeUTF(method.getName());
oos.writeUTF(beanName);
oos.flush();
ois = new ObjectInputStream(s.getInputStream());
Object obj = ois.readObject();
return obj;
} catch (Exception e) {
e.printStackTrace();
} finally {
if(null != ois) {
try {
ois.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if(null != oos) {
try {
oos.flush();
oos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
return null;
}
});
}
}
4. HelloService : 测试接口类
public interface HelloService {
String hello();
}
5. HelloServiceImpl: 测试接口实现类
public class HelloServiceImpl implements HelloService {
@Override
public String hello() {
System.out.println("RpcServer return hello world");
return "hello world";
}
}
6. RpcClient 测试类
public class RpcClient {
public static void main(String[] args) {
RpcServer rpcServer = new RpcServer();
// 异步启动服务端
new Thread(new Runnable() {
@Override
public void run() {
rpcServer.start();
}
}).start();
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("开始启动rpc客户端");
// 模拟客户端调用接口
for(int i = 0; i < 2; i++) {
HelloService helloService = (HelloService) RpcClientProxy.proxy(HelloService.class, "helloService");
String s = helloService.hello();
System.out.println(s);
}
}
}