简单介绍 RPC 框架

RPC 框架

在分布式服务框架中,一个最基础的问题就是远程服务是怎么通讯的,在 Java 领域中有很多可以实现远程通讯的技术,例如:RMI、Hessian、SOAP、ESB 和 JMS 等。其基本原理是基于传输协议和网络 IO 来实现,其中传输协议比较出名的有 TCP、UDP 等,TCP、UDP 都是基于 Socket 概念上为某类应用场景而扩展出来的传输协议。

RPC 概念

全称 remote procedure call,即远程过程调用。借助 RPC 可以做到像本地调用一样调用远程服务。RPC 并不是一个具体的技术,而是只整个网络远程调用过程

sequenceDiagram
方法 A - 方法 B: 本地调用
方法 B -- 方法 A: 结果返回
服务 1 服务 2 远程调用 返回结果 服务 1 服务 2

一个完整的 RPC 框架里边包含了四个核心的组件,分别是 Client,Client Stub,Server 以及 Server Stub,这个 Stub 可以理解为存根。

  • 客户端(Client),服务的调用方。
  • 客户端存根(Client Stub),存放服务端的地址消息,再将客户端的请求参数打包成网络消息,然后通过网络远程发送给服务方。
  • 服务端(Server),真正的服务提供者。
  • 服务端存根(Server Stub),接收客户端发送过来的消息,将消息解包,并调用本地的方法。

RMI

Java RMI,即远程方法调用 (Remote Method Invocation),一种用于实现远程调用(RPC-Remote procedure call)的 Java API,能直接传输序列化后的 Java 对象。RMI 的实现依赖于 Java 虚拟机,因此只能支持一个 JVM 到另一个 JVM 的调用。

代码示例使用

需求分析
  1. 服务端提供 ID 查询用户的方法
  2. 客户端调用服务端方法,并返回用户对象
  3. 要求使用 RMI 进行远程通讯
代码实现

服务端

/**
 * 服务端
 */
public class RMIServer {
    public static void main(String[] args) {
        try {
            //1.注册Registry实例. 绑定端口
            Registry registry = LocateRegistry.createRegistry(9998);
            //2.创建远程对象
            IUserService userService = new UserServiceImpl();
            //3.将远程对象注册到RMI服务器上即(服务端注册表上)
            registry.rebind("userService", userService);
            System.out.println("---RMI服务端启动成功----");
        } catch (RemoteException e) {
            e.printStackTrace();
        }
    }
}


客户端

/**
 * 客户端
 */
public class RMIClient {
    public static void main(String[] args) throws RemoteException, NotBoundException {
        //1.获取Registry实例
        Registry registry = LocateRegistry.getRegistry("127.0.0.1", 9998);
        //2.通过Registry实例查找远程对象
        IUserService userService = (IUserService) registry.lookup("userService");
        User user = userService.getByUserId(2);
        System.out.println(user.getId() + "----" + user.getName());
    }
}

接口及其实现类

public interface IUserService extends Remote {

    User getByUserId(int id) throws RemoteException;
}


public class UserServiceImpl extends UnicastRemoteObject implements IUserService {
    Map<Object, User> userMap = new HashMap();

    public UserServiceImpl() throws RemoteException {
        super();
        User user1 = new User();
        user1.setId(1);
        user1.setName("张三");
        User user2 = new User();
        user2.setId(2);
        user2.setName("李四");
        userMap.put(user1.getId(), user1);
        userMap.put(user2.getId(), user2);

    }

    @Override
    public User getByUserId(int id) throws RemoteException {
        return userMap.get(id);
    }
}

Netty 实现 RPC

需求分析

使用 Netty 实现一个简单的 RPC 框架,消费者和提供者约定接口和协议,消费者远程调用提供者的服务。

  • 创建一个接口,定义抽象方法。用于消费者和提供者之间的约定;
  • 创建一个提供者,该类需要监听消费者的请求,并按照约定返回数据;
  • 创建一个消费者,该类需要透明的调用自己不存在的方法,内部需要使用 Netty 进行数据通信
  • 提供者与消费者数据传输使用 json 字符串数据格式
  • 提供者使用 Netty 集成 Spring Boot 环境实现

代码实现

代码库:https://gitee.com/teaegg/netty-rpc.git

你可能感兴趣的:(netty,rpc,rpc,java,网络)