# spring-netty-rpc **Repository Path**: kun_gege/spring-netty-rpc ## Basic Information - **Project Name**: spring-netty-rpc - **Description**: 使用springboot+netty 完成rpc案例的书写 - **Primary Language**: Unknown - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2023-10-02 - **Last Updated**: 2023-10-03 ## Categories & Tags **Categories**: Uncategorized **Tags**: SpringBoot, Netty ## README ## netty 整合springboot 实现rpc ### 1. 模块介绍 - netty-client: netty的客户端,获取注册列表,调用远程方法 - netty-entity: 公共的类 - netty-register: 一个简单的注册中心 - netty-server : netty的服务端代码,注册到注册中心,执行客户端要执行的业务 #### 1.1 各个模块的包介绍 ![img_1.png](img_1.png) ![img_2.png](img_2.png) ### 2. 基本的流程图 ![img.png](img.png) ### 3. 扫描@Rpc注解的类 通过扫描指定的包下标注@Rpc注解的类来实现自动注册 #### 3.1 依赖 ```xml org.reflections reflections 0.9.11 ``` #### 3.2 实现 ```java /** * 程序启动时 * * @author kun.li */ @Component @Slf4j public class LocalRegisterScanner implements CommandLineRunner { String packageName = "com.lk.server"; @Override public void run(String... args) throws Exception { Reflections ref = new Reflections(packageName); Set> set = ref.getTypesAnnotatedWith(Rpc.class); for (Class aClass : set) { Rpc annotation = aClass.getAnnotation(Rpc.class); LocalRegister.register(aClass.getName(),annotation.version(),aClass.newInstance()); } } } ``` 在RequestMessageHandler 实现获取对应的类 ```java // 版本号 一个接口有多个实现类时进行区分 public Object version(String version, String interfaceName) { return LocalRegister.getService(interfaceName, version); } ``` ### 4.注意点 1. client 是一个长连接,获取client的channel时 需要保证获取的是本次连接的channel 2. client调用远程服务方法假设在main线程中,但是我们自定义的handler是在nio线程中,那么动态代理哪里如何获取到返回值? 我们可以使用netty中的Promise类来进行线程间数据共享,或者使用阻塞队列,ThreadLocal 都可以实现 3. 一个接口假如有多个实现类,该如何解决? 可以使用version来解决,client传递的requestMessage中加上一个version来区分,server在进行本地注册时 可以使用一个Map> 来进行注册 ### 5. 总结 通过本案例的书写,了解到了rpc的简单实现流程以及注册中心的简单实现流程 rpc:远程过程调用,http,tcp协议都属于rpc实现中的一种