文章详情

短信预约-IT技能 免费直播动态提醒

请输入下面的图形验证码

提交验证

短信预约提醒成功

RPC框架泛化调用原理及转转的实践

2024-12-13 15:35

关注

1、普通RPC调用

基于动态代理技术,RPC框架客户端做到了调用RPC方法与调用本地方法相同的体验。一般情况下服务端定义服务接口,并将接口打包到二方jar包发布。服务端在服务进程中实现该接口,而调用方在进程中根据该接口创建动态代理进行调用,与调用本地方法体验一致。

例如有接口HelloService​,被打包在demo-service-interfaces.jar包中。

public interface HelloService {
String hello(String name);
}

服务端依赖demo-service-interfaces.jar​,创建HelloServiceImpl实现该接口。

public class HelloServiceImpl implements HelloService {
@Override
public String hello(String name){
return "hello, " + name;
}
}

客户端同样依赖demo-service-interface.jar​,创建HelloService的代理类,以下为代码示例,实际上创建代理类,发送接口、参数,接收返回结果等操作都是封装在框架内的。

HelloService helloService = (HelloService)Proxy.newProxyInstance(this.getClass().getClassLoader(), HelloService.class, (InvocationHandler) (proxy, method, args) -> {
//都是封装在框架内的
//获取方法、参数类型
String methodName = method.getName();
Class<?>[] parameterTypes = method.getParameterTypes();
//发送方法、参数类型和实参到服务端并返回结果
return request(methodName, parameterTypes, args);
});
String result = helloService.hello("jack");
System.out.println(result);

2、网关、接口测试等场景下的需求

由上文可以看到普通的RPC调用需要将接口类(参数和返回值如果是POJO类型同样需要一起打包)打到一个jar包中,被服务方和调用方共同依赖。这种方式在多大数业务场景中是适用的,且更加方便,因为所依赖的接口jar包是可枚举的。

但是在一些特殊的场景下依赖接口jar包变得很不方便,比如网关、接口测试平台等。例如使用http网关代理私有协议RPC请求,如果在网关中依赖接口jar包,那么在新增方法或者接口时网关需要重新编译上线。而接口测试平台需要对全公司所有的RPC接口进行测试,将全公司所有的接口jar包添加到测试平台的依赖中显然是不可行的。

在这些场景下就诞生了对泛化调用的需求。

3、泛化调用

泛化调用就是在不依赖服务方接口jar包的情况下进行调用,包括对调用方法的泛化、参数的泛化和返回值的泛化。

public interface GenericService {
Object $genericInvoke(String methodName, String[] parameterTypes, Object[] args);
}

在没有接口类依赖的情况下,parameterTypes​需要通过字符串指定,而args​和返回值如果是jdk​内置类型的话与普通调用无异,而如果是POJO类型的话则需要寻找一种通用的表示方法。

下普通RPC调用的序列化与反序列化原理,如下图所示,实际上序列化框架在将POJO​序列化成字节数组之前需要解析POJO的类结构生成序列化中间体,当然序列化中间体并非一定能在序列化框架中找到对应的类,有时候这个中间体是虚拟的。

普通RPC调用序列化原理

3.1 基于Java Bean的泛化调用

基于Java Bean​的泛化调用是通过统一的Java Bean​描述符(JavaBeanDescriptor​)来描述POJO​对象,它工作在序列化层之上,例如dubbo​支持该种类型的泛化调用,在使用泛化调用时,直接传递JavaBeanDescriptor对象作为参数,基本原理如下图所示。

Java Bean泛化调用

该泛化调用的实现通用性比较强,与底层序列化无关,但是复杂度较高,需要RPC框架处理POJO和JavaBeanDescriptor之间的转换。

3.2 基于序列化中间体的泛化调用

支持基于序列化中间体的泛化调用的RPC框架典型的如sofa-rpc​,使用了sofa-hessian​序列化框架,sofa-hessian​是在hessian​序列化框架基础上进行二次开发的,抽象出了序列化中间体,如GenericObject、GenericMap、GenericArray等。

转转RPC框架在支持泛化调用时也参考了sofa-hessian​的实现,对hessian序列化框架进行二次开发,并且有所改进。

基于序列化中间体的泛化调用

而json​序列化天然具备序列化中间体,即JsonObject​或者json String​,在使用json​序列化时调用方可以直接将Json Object​或者json String​作为参数代替POJO​进行调用。转转RPC框架也支持基于json序列化的泛化调用。

dubbo​除了支持基于Java Bean​的泛化调用,还支持json-protobuf​泛化调用,也就是说调用方可以使用json​描述protobuf​对象,在反序列化时可以将json​反序列为protobuf​对象再转换成POJO,而这些功能本身是序列化框架所提供,不需要RPC框架做额外的开发支持。

基于序列化中间体的泛化调用与基于Java Bean的泛化调用相比,实现较为简单,有些序列化框架本身原生就支持,或者对序列化框架做简单的二次开发即可实现,缺点是与序列化框架耦合。

4、泛化调用在转转的实践

目前泛化调用在转转公司应用最广泛的领域就是接口测试,我们提供了统一的测试API平台。通过该平台可以使用http + json的方式实现对任意服务、任意节点、任意方法的调用,而测试API平台不需要依赖任何服务的接口jar包。并且API平台也没有依赖RPC框架jar包,因为转转RPC框架实现了在同一个端口上同时兼容私有的二进制协议及公有的http协议,也就是说可以使用http请求来发起RPC调用。

泛化调用在转转的应用

同时还支持获取任意服务、任意节点、任意方法参数及返回值的JsonSchema,如下代码所示。

{
"msg": "success",
"data": {
"schema": {
"returnValue": {
"type": "array",
"items": {
"type": "object",
"id": "urn:jsonschema:com:bj58:zhuanzhuan:arch:user:atomic:entity:User",
"properties": {
"id": {
"type": "string"
},
"userName": {
"type": "string"
},
"userNamePinyin": {
"type": "string"
},
"mock": {
"type": "boolean"
}
}
}
},
"parameters": {
"pageNum": {
"type": "integer"
},
"pageSize": {
"type": "integer"
}
}
}
},
"code": 0
}

未来转转的网关也将基于泛化调用进行开发。

5 总结

RPC框架的泛化调用在网关、测试平台等领域应用广泛,目前主流的泛化调用实现有基于Java Bean规范的泛化调用和基于序列化中间体的泛化调用,它们的优缺点分别如下:

在开发RPC框架时,具体选择哪种泛化调用实现方式,还需要结合实际情况做出选择。

关于作者

王建新,转转架构部服务治理负责人,主要负责服务治理、RPC框架、分布式调用跟踪、监控系统等。爱技术、爱学习,欢迎联系交流。

来源:转转技术内容投诉

免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

软考中级精品资料免费领

  • 历年真题答案解析
  • 备考技巧名师总结
  • 高频考点精准押题
  • 2024年上半年信息系统项目管理师第二批次真题及答案解析(完整版)

    难度     813人已做
    查看
  • 【考后总结】2024年5月26日信息系统项目管理师第2批次考情分析

    难度     354人已做
    查看
  • 【考后总结】2024年5月25日信息系统项目管理师第1批次考情分析

    难度     318人已做
    查看
  • 2024年上半年软考高项第一、二批次真题考点汇总(完整版)

    难度     435人已做
    查看
  • 2024年上半年系统架构设计师考试综合知识真题

    难度     224人已做
    查看

相关文章

发现更多好内容

猜你喜欢

AI推送时光机
位置:首页-资讯-后端开发
咦!没有更多了?去看看其它编程学习网 内容吧
首页课程
资料下载
问答资讯