RPC介绍
- 1 介绍
- 1.1 概述
- 1.2 RPC的分裂发展
- 2 历史发展
- 1969年11月,ARPAnet 开始建立。
- 1974年:Jon Postel 和 Jim White发表了RFC674
- 1975年:RFC684 作为RFC 674 的注释发表,对RFC 674 的争议进行回复。
- 1976年:RFC 707 发布
- 1983年1月1日,ARPA网将其网络核心协议由网络控制程序改变为 TCP/IP 协议
- 1984年:论文 《Implementing remote procedure calls》发表
- 1987年:《A Critique of the Remote Procedure Call Paradigm》发表
- 1988年,RFC 1057 发布,ONC RPC 被定义为标准的RPC 规范
- 1989年:Tim Berners-Lee 创建了万维网
- 1991年:OMG 发布CORBA 1.0
- 1994年:A Note on Distributed Computing 发布
- 1996年:HTTP/1.x 版本发布
- 1997年:OMG发布CORBA2.0
- 2002年:ZeroC Ice 发布
- 1999年:SOAP 发布(1998 年 XML 1.0 发布)
- 2000年:Roy Thomas Fielding 发表 RESTful 架构的博士论文
- 2008年,Vinoski 在他的论文中提出了我们开头的提问:“开发者的便利性真的比正确性、可扩展性、性能、关注点分离、可扩展性和偶然复杂度更重要吗?”
- 2008年:Google 开源 Protocol Buffer
- 2008年:FaceBook 开源 thrift
- 2010年5月:Avro脱离Hadoop项目,成为Apache顶级项目。
- 2015年:HTTP/2.0 发布
- 2015年:Google 开源gRPC
- 3 应用
- Linux系统支持
- 管道(Pipe)或者具名管道(Named Pipe)
- 信号(Signal)
- 信号量(Semaphore)
- 消息队列(Message Queue)
- 共享内存(Shared Memory)
- 套接字接口(Socket)
- 语言本身支持
- 一般实现
- 4 通信成本
- 5 各类RPC介绍
- RAW socket
- COM/COM+/DCOM
- CORBA
- XML-RPC / SOAP
- ESB
- WCF
- DDS
- REST
- Google的gRPC
- JSON-RPC
- 阿里巴巴的HSF(好舒服),Dubbo(开源)
- Facebook的Thrift(开源)
- Twitter的Finagle(开源)
- 微博平台的Motan
- 参考
1 介绍
1.1 概述
- 在分布式计算中,远程过程调用( RPC ) 是指计算机程序引起过程(子例程)在不同的地址空间中执行(通常在共享网络上的另一台计算机上),编写起来就好像它是一个普通的(本地)过程调用,而无需程序员明确编写远程交互的细节。也就是说,无论子例程对于正在执行的程序是本地的还是远程的,程序员编写的代码本质上是相同的。这是一种客户端-服务器交互形式(调用者是客户端,执行者是服务器),通常通过请求-响应消息传递系统实现。
- RPC 是进程间通信 (IPC) 的一种形式,因为不同的进程具有不同的地址空间:如果在同一台主机上,它们具有不同的虚拟地址空间,即使物理地址空间相同;而如果它们在不同的主机上,则物理地址空间是不同的。许多不同的(通常是不兼容的)技术已被用来实现这个概念。
- RPC 是一种请求-响应协议,实现程序与程序之间的交流。
1.2 RPC的分裂发展
- 简单、普适、高性能这三点,是RPC的追求,目前没有哪一个真正做到。
- 相继出现过 RMI(Sun/Oracle)、Thrift(Facebook/Apache)、Dubbo(阿里巴巴/Apache)、gRPC(Google)、Motan1/2(新浪)、Finagle(Twitter)、brpc(百度/Apache)、.NET Remoting(微软)、Arvo(Hadoop)、JSON-RPC 2.0(公开规范,JSON-RPC 工作组)……等等难以穷举的协议和框架。这些 RPC 功能、特点不尽相同,有的是某种语言私有,有的能支持跨越多门语言,有的运行在应用层 HTTP 协议之上,有的能直接运行于传输层 TCP/UDP 协议之上,但肯定不存在哪一款是“最完美的 RPC”。今时今日,任何一款具有生命力的 RPC 框架,都不再去追求大而全的“完美”,而是有自己的针对性特点作为主要的发展方向。
- 追求面向对象,代表为 RMI、.NET Remoting,之前的 CORBA 和 DCOM 也可以归入这类。
- 追求性能,代表为 gRPC 和 Thrift。决定 RPC 性能的主要就两个因素:序列化效率和信息密度。
- 追求简化,代表为 JSON-RPC,说要选功能最强、速度最快的 RPC 可能会很有争议,但选功能弱的、速度慢的,JSON-RPC 肯定会候选人中之一。牺牲了功能和效率,换来的是协议的简单轻便,接口与格式都更为通用,尤其适合用于 Web 浏览器这类一般不会有额外协议支持、额外客户端支持的应用场合。
2 历史发展
1969年11月,ARPAnet 开始建立。
1996年,美国国防部高级研究计划管理局(ARPA全称:Advanced Research Projects Agency)开始建立一个命名为ARPAnet的网络。最开始只有4个结点,分别是洛杉矶的加利福尼亚州大学洛杉矶分校、加州大学圣巴巴拉分校、斯坦福大学、犹他州大学四所大学的4台大型计算机。选择这四个节点的一个原因是要测试不同类型主机联网的兼容性。
1974年:Jon Postel 和 Jim White发表了RFC674
过程调用最早可以追溯到 Jon Postel 和 Jim White 在1974 年发表的 Procedure Call Protocol Documents Version 2(RFC674)。这个协议试图定义一种通用的方法,用于解决 NSW 项目中多个计算节点通信的问题。
协议发表后,引起了非常大的争议,1975年,RFC674的注释篇RFC684 发布。
1975年:RFC684 作为RFC 674 的注释发表,对RFC 674 的争议进行回复。
RFC 684 不是一个独立的协议, 主要对 RFC674 的争议进行讨论。
1976年:RFC 707 发布
1983年1月1日,ARPA网将其网络核心协议由网络控制程序改变为 TCP/IP 协议
1984年:论文 《Implementing remote procedure calls》发表
RPC 是远程过程调用(Remote Procedure Call)的缩写形式,Birrell 和 Nelson 在 1984 发表于 ACM Transactions on Computer Systems 的论文《Implementing remote procedure calls》对 RPC 做了经典的诠释。RPC 是指计算机 A 上的进程,调用另外一台计算机 B 上的进程,其中 A 上的调用进程被挂起,而 B 上的被调用进程开始执行,当值返回给 A 时,A 进程继续执行。调用方可以通过使用参数将信息传送给被调用方,而后可以通过传回的结果得到信息。而这一过程,对于开发人员来说是透明的。之后的几年RPC一直被认为是建立分布式操作系统的最合适的范式。
1987年:《A Critique of the Remote Procedure Call Paradigm》发表
1987年,Tanenbaum 和 Renesse发表文章《A Critique of the Remote Procedure Call Paradigm》,讨论了RPC 模型的概念问题、实现技术问题、客户端和服务端崩溃后的处理问题、不同系统间的问题以及性能等多方面的问题,并对存在的问题进行了分析。
1988年,RFC 1057 发布,ONC RPC 被定义为标准的RPC 规范
Sun 公司是第一个提供商业化 RPC 库和 RPC 编译器。在1980年代中期, Sun 计算机提供 RPC,并在 Sun Network File System(NFS) 得到支持。该协议被主要以 Sun 和 AT&T 为首的 Open Network Computing (开放网络计算)作为一个标准来推动。这是一个非常轻量级 RPC 系统,可用在大多数 POSIX 和类 POSIX 操作系统中使用,包括 Linux、SunOS、OS X 和各种发布版本的 BSD。这样的系统被称为 Sun RPC 或 ONC RPC。最终sun成功了,sunrpc 成了第一个rpc的标准。
1989年:Tim Berners-Lee 创建了万维网
1989年,蒂姆·伯纳斯-李发明了万维网。第二年9月,开发了第一个网页浏览器。到1990年圣诞节,蒂姆·伯纳斯-李创建运行万维网所需的所有工具:超文本传输协议(HTTP)、超文本标记语言(HTML)、第一个网页浏览器、第一个网页服务器和第一个网站,实现了超文本传输协议客户端与服务器的第一次通讯。他也因此而获得了2016年的图灵奖。到1995年,互联网在美国已完全商业化。
1991年:OMG 发布CORBA 1.0
OMG成立于1989年,作为一个非营利性组织,集中致力于开发在技术上具有先进性、在商业上具有可行性并且独立于厂商的软件互联规范,推广面向对象模型技术,增强软件的可移植性(Portability)、可重用性(Reusability)和互操作性(Interoperability)。CORBA 试图为应用程序开发人员提供几个好处: 语言独立性、操作系统独立性、体系结构独立性、通过 IDL 中的抽象类型映射到这些类型的机器和语言特定实现的静态类型,以及对象传输,其中对象可以通过不同机器之间的连接进行迁移。
1994年:A Note on Distributed Computing 发布
Jim Waldo 等人发表了一篇 名为 《A Note on Distributed Computing》的论文。 这篇论文详细讨论了为什么 RPC 模型扩展到对象,是有问题的。作者认为,远程计算的问题主要有通信时延、地址空间隔离、局部故障、并发问题。
1996年:HTTP/1.x 版本发布
1996 年,HTTP/1.0 版本发布,大大丰富了 HTTP 的传输内容,除了文字,还可以发送图片、视频等,这为互联网的发展奠定了基础。在 HTTP/1.0 发布几个月后,HTTP/1.1 就发布了。HTTP/1.1 更多的是作为对 HTTP/1.0 的完善。
1997年:OMG发布CORBA2.0
1994年12月,CORBA 2.0 就已经发布规范,该规范希望能够解决不同厂商根据COBRA规范所开发的产品“互联互不通”的严重问题,但直到1997年,Corba2.0 才正式发布,但是最后还是失败了。至于COBRA失败的原因,COBRA阵营的技术大牛、COBRA技术的推动者,即后来加入反COBRA阵营的Michi Henning,在他的《The rise and fall of CORBA》书里做了如下深刻的总结。规范巨大而复杂、CORBA学习曲线陡峭、编程开发过于复杂、费用昂贵、Sun与Java成为COBRA最大的竞争对手【转向Web】、XML技术的兴起加速了COBRA的没落。
2002年:ZeroC Ice 发布
最初参与CORBA 的一批技术专家不满CORBA 的设计,另起炉灶打造了新的RPC—即 ZeroC Ice,ICE 最初的广告语为“反叛之冰”。它也一直延续至今,发展成了一个强大的微服务架构平台。
1999年:SOAP 发布(1998 年 XML 1.0 发布)
1998 年 XML 1.0 发布,被 W3C (World Wide Web Consortium) 推荐为标准的描述语言。同年,微软和DevelopMentor发布SOAP(Simple Object Access Protocol),随后提交给W3C作为标准。SOAP是一个严格定义的信息交换协议,使用XML作为RPC新的对象序列化机制,用于在Web Service中把远程调用和返回封装成机器可读的格式化数据。
2000年:Roy Thomas Fielding 发表 RESTful 架构的博士论文
2000年,Roy Thomas Fielding 博士在他的博士论文 《Architectural Styles and the Design of Network-based Software Architectures》首次提出了 REST 这个词。
REST提供了一系列架构约束,当作为整体使用时,它强调组件交互的可扩展性、接口的通用性、组件的独立部署,以及那些能减少交互延迟的中间件,它强化了安全性,也能封装遗留系统。
2008年,Vinoski 在他的论文中提出了我们开头的提问:“开发者的便利性真的比正确性、可扩展性、性能、关注点分离、可扩展性和偶然复杂度更重要吗?”
为什么学习曲线陡峭、设计复杂的Rust 是程序员的最爱?
为什么易学易用但有各种语言缺陷的JavaScript 能成为最流行的语言呢?
开发者的便利性比正确性、可扩展性、性能、关注点分离、可扩展性和偶然复杂度更重要。
2008年:Google 开源 Protocol Buffer
Protocol Buffers 是一种轻便高效的结构化数据存储格式,可以用于结构化数据序列化,很适合做数据存储或 RPC 数据交换格式。它可用于通讯协议、数据存储等领域的语言无关、平台无关、可扩展的序列化结构数据格式。
2008年:FaceBook 开源 thrift
Thrift 是一个跨语言的服务部署框架,最初由Facebook于2007年开发,2008年进入Apache开源项目。Thrift通过一个中间语言(IDL, 接口定义语言)来定义RPC的接口和数据类型,然后通过一个编译器生成不同语言的代码(目前支持C++,Java, Python, PHP, Ruby, Erlang, Perl, Haskell, C#, Cocoa, Smalltalk和OCaml),并由生成的代码负责RPC协议层和传输层的实现。
Thrift 和 Protocol Buffer 不同,它不仅仅是一个数据序列化工具,而是一个完整的RPC 框架。另一个不同点在于,Protobuf 标准化了单一的二进制编码方式,但Thrift 则包含了多种不同的序列化方式(Thirft 称之为协议)。
2010年5月:Avro脱离Hadoop项目,成为Apache顶级项目。
Avro 是一个基于二进制数据传输高性能的中间件,在2009年成为 Hadoop 中的一个子项目,并与2015年脱离Hadoop,加入Apache成为一个独立的项目。Avro 同样支持跨编程语言实现(C, C++, C#,Java, Python, Ruby, PHP),Avro 提供着与诸如 Thrift 和 Protocol Buffers 等系统相似的功能。
2015年:HTTP/2.0 发布
在 2010 年到 2015 年,谷歌通过实践一个实验性的 SPDY 协议,证明了一个在客户端和服务器端交换数据的另类方式。其收集了浏览器和服务器端的开发者的焦点问题,明确了响应数量的增加和解决复杂的数据传输。SPDY 最终进化成了HTTP2.0 并于2015年发布。使用二进制分帧层、多路复用、数据流优先级、服务端推送、头部压缩。
2015年:Google 开源gRPC
2015 年,Google 将gRPC框架开源,gRPC 使用 PB 作为序列化的解决方案,而在传输的介质上使用了 HTTP/2而不是常见的TCP。gRPC 是一个多路复用、双向流式 RPC 协议。在一般的 RPC 机制中,客户端发起到服务器的连接,只有客户端可以请求,而服务器只能响应传入的请求。然而,在双向 gRPC 流中,虽然初始连接是由客户端发起的(称为端点1) ,但是一旦建立连接,服务器(称为端点2)和端点1都可以发送请求和接收响应。这极大地简化了两个端点相互通信的开发(如网格计算)。由于两个数据流都是独立的,这也省去了在端点之间创建两个独立连接的麻烦(一个从端点1到端点2,另一个从端点2到端点1)。
3 应用
Linux系统支持
管道(Pipe)或者具名管道(Named Pipe)
管道类似于两个进程间的桥梁,可通过管道在进程间传递少量的字符流或字节流。普通管道只用于有亲缘关系进程(由一个进程启动的另外一个进程)间的通信,具名管道摆脱了普通管道没有名字的限制,除具有管道所有的功能外,它还允许无亲缘关系进程间的通信。管道典型的应用就是命令行中的|操作符,譬如:
ps -ef | grep C++
信号(Signal)
信号用于通知目标进程有某种事件发生,除了用于进程间通信外,进程还可以发送信号给进程自身。信号的典型应用是kill命令,譬如:
kill -9 pid
信号量(Semaphore)
信号量用于两个进程之间同步协作手段,它相当于操作系统提供的一个特殊变量,程序可以在上面进行wait()和notify()操作。
消息队列(Message Queue)
以上三种方式只适合传递传递少量信息,POSIX 标准中定义了消息队列用于进程间数据量较多的通信。进程可以向队列添加消息,被赋予读权限的进程则可以从队列消费消息。消息队列克服了信号承载信息量少,管道只能用于无格式字节流以及缓冲区大小受限等缺点,但实时性相对受限。
共享内存(Shared Memory)
允许多个进程访问同一块公共的内存空间,这是效率最高的进程间通信形式。原本每个进程的内存地址空间都是相互隔离的,但操作系统提供了让进程主动创建、映射、分离、控制某一块内存的程序接口。当一块内存被多进程共享时,各个进程往往会与其它通信机制,譬如信号量结合使用,来达到进程间同步及互斥的协调操作。
套接字接口(Socket)
消息队列和共享内存只适合单机多进程间的通信,套接字接口是更为普适的进程间通信机制,可用于不同机器之间的进程通信。套接字(Socket)起初是由 UNIX 系统的 BSD 分支开发出来的,现在已经移植到所有主流的操作系统上。出于效率考虑,当仅限于本机进程间通信时,套接字接口是被优化过的,不会经过网络协议栈,不需要打包拆包、计算校验和、维护序号和应答等操作,只是简单地将应用层数据从一个进程拷贝到另一个进程,这种进程间通信方式有个专名的名称:UNIX Domain Socket,又叫做 IPC Socket。
语言本身支持
- Java的Java 远程方法调用(Java RMI) API 提供与标准 Unix RPC 方法类似的功能。
- Go提供了rpc 包来实现 RPC,支持异步调用。
- Modula-3的网络对象,它是 Java 的 RMI [10]的基础
- RPyC在 Python 中实现了 RPC 机制,支持异步调用。
- 分布式 Ruby (DRb) 允许 Ruby 程序在同一台机器上或通过网络相互通信。DRb 使用远程方法调用 (RMI) 在进程之间传递命令和数据。
- Erlang是面向过程的,并且通过在节点和本地进程之间传递类似的消息来原生支持分发和 RPC。
- Elixir建立在 Erlang VM 之上,并允许通过代理和消息传递开箱即用地在同一网络中进行进程通信(Elixir/Erlang 进程,而不是操作系统进程)。
一般实现
- NFS(网络文件系统)是RPC最突出的用户之一
- 开放网络计算远程过程调用,Sun Microsystems
- D-Bus开源IPC程序提供与CORBA类似的功能。
- SORCER为联合方法调用提供 API 和面向用力的语言 (EOL)
- XML-RPC是一种 RPC 协议,它使用XML对其调用进行编码,并使用HTTP作为传输机制。
- JSON-RPC是一种使用JSON编码消息的RPC 协议
- JSON-WSP是一种使用JSON编码消息的RPC 协议
- SOAP是 XML-RPC 的后继者,也使用 XML 对其基于 HTTP 的调用进行编码。
- ZeroC的Internet 通信引擎(Ice) 分布式计算平台。
- 用于构建网络服务的Etch框架。
- Apache Thrift协议和框架。
- CORBA通过称为对象请求代理的中间层提供远程过程调用。
- Libevent提供了一个用于创建 RPC 服务器和客户端的框架。
- Windows Communication Foundation是 .NET 框架中的一个应用程序编程接口,用于构建连接的、面向服务的应用程序。
- Microsoft .NET Remoting为在 Windows 平台上实现的分布式系统提供 RPC 功能。它已被WCF取代。
- Microsoft DCOM使用基于DCE/RPC的MSRPC
- 开放软件基金会DCE/RPC分布式计算环境(也由 Microsoft 实施)。
- Google Protocol Buffers (protobufs) 包包括一种用于其 RPC 协议[12]的接口定义语言,该语言于 2015 年作为gRPC开源。
- WAMP将 RPC 和发布-订阅组合成一个独立于传输的协议。
- Google Web Toolkit使用异步 RPC 与服务器服务通信。
- Apache Avro提供 RPC,其中不需要客户端和服务器在连接握手和代码生成中交换模式。
4 通信成本
1987 年,在“透明的 RPC 调用”一度成为主流范式的时候,Andrew Tanenbaum 教授曾发表了论文《A Critique of The Remote Procedure Call Paradigm》,对这种透明的 RPC 范式提出了一系列质问:
- 两个进程通信,谁作为服务端,谁作为客户端?
- 怎样进行异常处理?异常该如何让调用者获知?
- 服务端出现多线程竞争之后怎么办?
- 如何提高网络利用的效率,譬如连接是否可被多个请求复用以减少开销?是否支持多播?
- 参数、返回值如何表示?应该有怎样的字节序?
- 如何保证网络的可靠性?譬如调用期间某个链接忽然断开了怎么办?
- 发送的请求服务端收不到回复该怎么办?
- ……
多年发展逐渐证明 Andrew Tanenbaum 的预言是正确的。最终,到 1994 年至 1997 年间,由 ACM 和 Sun 院士Peter Deutsch、套接字接口发明者Bill Joy、Java 之父James Gosling等一众在 Sun Microsystems 工作的大佬们共同总结了通过网络进行分布式运算的八宗罪(8 Fallacies of Distributed Computing):
- The network is reliable —— 网络是可靠的。
- Latency is zero —— 延迟是不存在的。
- Bandwidth is infinite —— 带宽是无限的。
- The network is secure —— 网络是安全的。
- Topology doesn’t change —— 拓扑结构是一成不变的。
- There is one administrator —— 总会有一个管理员。
- Transport cost is zero —— 不必考虑传输成本。
- The network is homogeneous —— 网络是同质化的。
5 各类RPC介绍
RAW socket
C/S架构间,自定义协议,例如 TLV(Type-Length-Value),两侧需要对照报文进行序列化和反序列化。该模式比较常用,一些轻框架的小应用,这么用程序小,效率高。
不过需要自己解决粘包拆包,线程池优化,大文件传输等问题。
TLV: TLV是指由数据的类型Tag,数据的长度Length,数据的值Value组成的结构体,几乎可以描任意数据类型,TLV的Value也可以是一个TLV结构,正因为这种嵌套的特性,可以让我们用来包装协议的实现。
COM/COM+/DCOM
COM(组件对象模型,Component Object Model)技术的目标是让使用不同语言编写、运行在不同进程甚至不同计算机中的程序可以通过组件对象模型来进行统一建模,使得不同程序之间可以用同样的方式来调用彼此。
后来逐步迭代到COM+、DCOM。
微软提出的 COM 最后因为过度抽象并没有大范围应用。
CORBA
CORBA,Common Object Request Broker Architecture,公共对象请求代理体系结构。由OMG组织制订的一种标准的面向对象应用程序体系规范。或者说 CORBA体系结构是OMG为解决分布式处理环境(DCE)中,硬件和软件系统的互连而提出的一种解决方案。
现在CORBA用的已经很少了,基本上只有一些大的电信项目还在用,现在同类的解决方案中WebService是比较流行的。
《The Rise and Fall of CORBA》一文中,比较详细的介绍了为什么CORBA会衰落。总结起来有几点:
- 标准不够完善,导致各个商业版本的实现不一致(后来的Web其实也有这个问题);
- 功能跟不上时代,互联网的快速发展对于安全通信提出了需求,但CORBA并没有提供这方面的支持;
- 接口定义复杂,暴露过多细节,对开发人员要求高,容易出现bug;
XML-RPC / SOAP
XML-RPC发表于1998年,由UserLand Software(UserLand Software)的Dave Winer及Microsoft共同发表。后来在新的功能不断被引入下,这个标准慢慢演变成为今日的SOAP协议。
SOAP能够在企业级软件开发中生存很久,很重要的一个原因是,大家在工作中用到的OA系统、报表工具、CRM系统等,即使慢如蜗牛,大家也不会太多抱怨,趁着网页卡在那里的时间,正好喝喝茶,聊聊天;而CTO们更不会有抱怨了,因为他们只负责买,又不负责用。
ESB
ESB(企业服务总线)借着SOA概念的流行,在2000年之后快速兴起。
ESB的初衷是好的,它希望能够在SOAP的基础上,解决其只能点对点路由的问题,同时还可以兼容不同通信协议。但是,为了解决一个问题,它引入了另一个问题,就是业务逻辑与ESB绑定,导致ESB变得越来越不“单纯”,最后ESB越来越大,越来越复杂,越来越难以维护,最后就成了整个系统的痼疾。
WCF
WCF是微软在实现大一统梦想的路上,推出的又一力作。WCF继承了COM的衣钵,希望以一种统一的方式,将TCP通信、HTTP服务、SOAP服务、REST服务等等,都封装起来,在开发者看来,都是一个本地方法调用。
DDS
- CORBA的快速陨落,让CORBA的提出者OMG痛定思痛,重新提出了一个标准——DDS(Data Distribution Service,数据分发服务)。这个标准最早在2001年开始成形,2003年DDS 1.0标准正式提出。
- DDS的基础是以发布订阅(Publishi-subscribe)的方式进行无中心的实时数据传输,支持QoS定义,可水平扩展等能力。这是一个工业级的数据协议,早期是用在仪器设备之间进行实时数据通信,在美国有些军用设备上也有使用,后来开始用在金融、航空领域,物联网,无人驾驶,机器人等行业使用。
- 作为实时数据传输协议,商用的DDS实现可以做到微秒级别的延时,同时还可以支撑大规模并发通信。时至今日,互联网技术圈中以性能著称的消息服务Kafka,在性能指标上依然难以望其项背。
- DDS之所以能够做到这么快,是因为它的RTPS协议(Real-Time Publish-Subscribe Protocol,实时发布订阅协议),这个协议是基于UDP的,通过ACK心跳和消息接收回执来保证消息的送达,避免了TCP协议漫长的三次握手。但用UDP也有一个问题,就是不能跨网段,于是有公司提出通过一个中心的桥接器,以TCP连接将两个私有网络连接起来,私有网络内部采用UDP通信。
- DDS在工业领域其实很火,在互联网领域只是大家没有听说;其次,目前大部分DDS的实现都是商用版本,要想使用,需要付高额的授权费用。DDS因为需要在计算机上安装RTPS协议栈,对于服务器的侵入性比较强。其带来的从毫秒级别到微秒级别的提升,对于互联网公司的服务对象(主要是人)来说,感受并不明显。
REST
REST(Representational State Transfer,表述性状态转移)是当今最为流行的API。因为大量的Web应用采用REST作为其API的选择。REST是Roy Thomas Fielding博士于2000年在他的博士论文中提出来的一种万维网软件架构风格。
SOAP仅仅将HTTP作为一种可选的数据传输方式,REST则是带着HTTP基因出生的。首先,REST将服务间通信进行了一次抽象,所有的服务交互都建模成对资源的CRUD操作;其次,它充分利用了HTTP协议中丰富的动词,遵循约定大于配置的互联网开发哲学,避免了复杂和冗余的方法定义;再次,由于通过HTTP的动词可以明确区分读写操作,对于GET类的读操作,还可以通过缓存或者CDN进行加速;最后,采用JSON或者XML等通用格式来描述数据,简单,直接。基于这几点,REST开始在互联网领域大行其道。
Google的gRPC
JSON-RPC
如果选功能弱的、速度慢的,JSON-RPC 肯定会候选人中之一。牺牲了功能和效率,换来的是协议的简单轻便,接口与格式都更为通用,尤其适合用于 Web 浏览器这类一般不会有额外协议支持、额外客户端支持的应用场合。
阿里巴巴的HSF(好舒服),Dubbo(开源)
Facebook的Thrift(开源)
Twitter的Finagle(开源)
微博平台的Motan
参考
1、wiki–Remote procedure call
2、编程十年之那些年我见过和用过的RPC
3、序列化与反序列化深入理解
4、OMG–IDL(Interface Definition Language)
5、软件架构–服务架构演进
6、远程服务调用
7、RPC 发展史
8、那些年,我们追过的RPC