在软件开发中,通信协议扮演着关键的角色,它们定义了不同系统或组件之间进行通信的规则和方式。HTTP(Hypertext Transfer Protocol)和RPC(Remote Procedure Call Protocol)是两种常见的通信协议。然而RPC 和 HTTP 并不是同一个维度的两个概念。只不过都可以作为远程调用的,所以经常拿来对比。
HTTP
HTTP被译为超文本传输协议,就是一种传输协议。
HTTP工作原理
HTTP协议定义Web客户端如何从Web服务器请求Web页面,以及服务器如何把Web页面传送给客户端。HTTP协议采用了请求/响应模型。客户端向服务器发送一个请求报文,请求报文包含请求的方法、URL、协议版本、请求头部和请求数据。服务器以一个状态行作为响应,响应的内容包括协议的版本、成功或者错误代码、服务器信息、响应头部和响应数据。
以下是 HTTP 请求/响应的步骤:
-
客户端连接到Web服务器
一个HTTP客户端,通常是浏览器,与Web服务器的HTTP端口(默认为80)建立一个TCP套接字连接。例如,http://www.baidu.com。 -
发送HTTP请求
通过TCP套接字,客户端向Web服务器发送一个文本的请求报文,一个请求报文由请求行、请求头部、空行和请求数据4部分组成。 -
服务器接受请求并返回HTTP响应
Web服务器解析请求,定位请求资源。服务器将资源复本写到TCP套接字,由客户端读取。一个响应由状态行、响应头部、空行和响应数据4部分组成。 -
释放连接TCP连接
若connection 模式为close,则服务器主动关闭TCP连接,客户端被动关闭连接,释放TCP连接;若connection 模式为keepalive,则该连接会保持一段时间,在该时间内可以继续接收请求; -
客户端浏览器解析HTML内容
客户端浏览器首先解析状态行,查看表明请求是否成功的状态代码。然后解析每一个响应头,响应头告知以下为若干字节的HTML文档和文档的字符集。客户端浏览器读取响应数据HTML,根据HTML的语法对其进行格式化,并在浏览器窗口中显示。
例如:在浏览器地址栏键入URL,按下回车之后会经历以下流程:
1. 浏览器向 DNS 服务器请求解析该 URL 中的域名所对应的 IP 地址;
2. 解析出 IP 地址后,根据该 IP 地址和默认端口 80,和服务器建立TCP连接;
3. 浏览器发出读取文件(URL 中域名后面部分对应的文件)的HTTP 请求,该请求报文作为 TCP 三次握手的第三个报文的数据发送给服务器;
4. 服务器对浏览器请求作出响应,并把对应的 html 文本发送给浏览器;
5. 释放 TCP连接;
6. 浏览器将该 html 文本并显示内容;
RPC
RPC 被译为远程过程调用。
一种解释:
RPC 本质上不算是协议,而是一种调用方式,而像 gRPC 和 Thrift 这样的具体实现,才是协议,它们是实现了 RPC 调用的协议。要想实现 RPC 通常需要包含传输协议和序列化协议的实现。一个通俗的描述是:客户端在不知道调用细节的情况下,调用存在于远程计算机上的某个对象,就像调用本地应用程序中的对象一样。比较正式的描述是:一种通过网络从远程计算机程序上请求服务,而不需要了解底层网络技术的协议。
RPC基于TCP协议,客服端与服务端需要进行三次握手完成可靠连接,第四步进行数据传输。因为TCP是数据传输层,传输协议需要服务器统一编写,进行二进制传输,依赖序列化和反序列化规则,对于大部分应用需要灵活变动数据则不适用,RPC常用于Socket连接或一些基本不变动的传输格式数据,减少数据变动带来的开发成本。
建立Socket连接至少需要一对套接字,其中一个运行于客户端,称为ClientSocket ,另一个运行于服务器端,称为ServerSocket ,套接字之间的连接过程分为三个步骤:服务器监听,客户端请求,连接确认。
另外一种解释:
RPC是一种进程间通信方式,是一种技术的思想,而不是规范。它允许程序调用另一个地址空间(通常是共享网络的另一台机器上)的过程或函数,而不用程序员显式编码这个远程调用的细节。即程序员无论是调用本地的还是远程的函数,本质上编写的调用代码基本相同。
通俗的说法就是:比如说现在有两台服务器A和B,一个应用部署在A服务器上,另一个应用部署在B服务器上,如果A应用想要调用B应用提供的方法,由于他们不在一台机器下,也就是说它们不在一个JVM内存空间中,是无法直接调用的,需要通过网络进行调用,那这个调用过程就叫做RPC。
RPC两个核心模块:通讯,序列化。
注意:无论是何种类型的数据,最终都需要序列化转换成二进制流在网络上进行传输,数据的发送方需要将对象序列化转换为二进制流,而数据的接收方则需要把二进制流反序列化为对象。
RPC框架
在RPC框架中主要有三个角色:Provider、Consumer和Registry。如下图所示:
Server:暴露服务的服务提供方;
Client:调用远程服务的服务消费方;
Registry:服务注册与发现的注册中心。
实现RPC需要用到的技术
一个成熟的RPC框架需要考虑的问题有很多,这里只介绍实现一个远程调用需要用到的基本技术,感兴趣的朋友可以找一些开源的RPC框架代码来看下。
动态代理
生成client stub和server stub需要用到Java动态代理技术,我们可以使用JDK原生的动态代理机制,可以使用一些开源字节码工具框架,如:CgLib、Javassist等。
序列化
为了能在网络上传输和接收Java对象,我们需要对它进行序列化和反序列化操作。
可以使用Java原生的序列化机制,但是效率非常低,推荐使用一些开源的、成熟的序列化技术,例如:protobuf、Thrift、hessian、Kryo、Msgpack。
NIO
当前很多RPC框架都直接基于netty这一IO通信框架,比如阿里巴巴的HSF、dubbo,Hadoop Avro,推荐使用Netty作为底层通信框架。
服务注册中心
可选技术:Redis、Zookeeper、Consul
RPC和HTTP的区别
方式 | 相同点 | 不同 | 特性 | 速度 | 难度 | 通信协议 | 应用场景 |
RPC | 都是客户端发起请求,服务端响应 | RPC需要满足像调用本地服务一样调用远程服务,也就是对调用过程在API层面进行封装 | RPC更加透明,对用户方便。RPC需要在API层面进行封装,限制了开发的语言环境 | RPC速度比HTTP快,底层都是TCP,HTTP消息往往比较臃肿,但是可以采用gzip压缩 | RPC实现有点儿复杂,HTTP相对比较简单 | RPC使用二进制协议 | |
HTTP | 都是客户端发起请求,服务端响应 | Http协议没有这样的要求,因此请求、响应等细节需要我们自己去实现 | HTTP方式更加灵活,没有规定API和语言,跨语言,跨平台 | HTTP使用文本协议 | 微服务,强调独立,自治,灵活。RPC限制较多,因此微服务框架中,一般都会采用基于HTTP的rest风格服务 |
最本质的区别,就是 RPC 主要是基于 TCP/IP 协议的,而 HTTP 服务主要是基于 HTTP 协议的。我们都知道 HTTP 协议是在传输层协议 TCP 之上的,从效率来看的话,RPC 当然是要更胜一筹啦。
调用方式不同:HTTP接口通过URL(Uniform Resource Locator,统一资源定位符,是全球互联网上标识和定位资源的标准格式。URL不仅提供了资源的位置,还可以包含其他信息,比如访问协议、主机名、端口号、路径和查询参数等。它是Web访问的基本组成部分,使得用户可以方便地访问所需的信息)进行调用,RPC接口通过函数调用进行调用。
通信方式不同:RPC是一种进程间通信方式。双方建立链接后,一个进程可以直接调用另一个进程的函数。HTTP是一种客户端和服务器之间的请求-响应模式。客户端发送请求,服务器返回响应,两者连接后立即断开。
Spring Cloud 远程调用为啥要采用 HTTP,而不是 RPC
SpringCloud开启Web服务依赖于内部封装的Tomcat容器,而今信息飞速发展,适应大流量的微服务,采用Tomcat处理HTTP请求,开发者编写json作为资源传输,服务器做出相应的响应,可以更加的灵活处理业务数据,而HTTP协议是跨平台的,符合微服务B/C数据交互的方式,可以的一套服务器对应移动H5、App、小程序提供服务。
1.HTTP的跨平台与灵活性
HTTP作为互联网上的通用协议,具有天然的跨平台特性。无论是Web应用、移动App、还是小程序,都可以通过HTTP协议与服务器进行通信。在微服务架构中,这种跨平台能力尤为重要,因为它允许一套服务同时支持多种客户端的访问。而RPC虽然能够实现远程调用,但通常基于特定的协议(如TCP),这在一定程度上限制了其跨平台的能力。
2.HTTP的易用性与广泛性
HTTP协议简单易用,拥有广泛的工具和库支持。开发者可以使用各种现成的HTTP客户端和服务器库来构建微服务系统,无需从头开始实现复杂的通信协议。相比之下,RPC虽然能够提供更高效的远程调用方式,但其实现通常较为复杂,需要开发者编写额外的序列化和反序列化代码,以及处理网络通信的细节。
3.SpringCloud的集成优势
SpringCloud为开发者提供了一套完整的微服务解决方案,包括服务注册与发现、负载均衡、断路器、智能路由等功能。这些功能大多基于HTTP协议进行通信,使得SpringCloud在集成HTTP服务时具有天然的优势。例如,SpringCloud中的Feign客户端和Zuul网关都是基于HTTP协议实现的,它们能够轻松地与HTTP服务进行交互,而无需额外的配置或转换。
4.HTTP的扩展性与标准化
HTTP协议具有良好的扩展性,可以通过添加HTTP头或更改请求体来携带额外的信息。这种灵活性使得HTTP能够适应各种复杂的业务需求。同时,HTTP协议也是标准化的,这意味着不同的系统和平台都能够理解和处理HTTP请求和响应。相比之下,RPC协议通常是私有的,不同的RPC框架之间可能存在兼容性问题。
结论:微服务强调独立,自治,灵活。RPC限制较多,因此微服务框架中,一般都会采用基于HTTP的rest风格服务。