一、前言
首先我们说下,什么是服务调用?其实就是两个服务器之间能够进行通信,完成某种请求与响应的过程。
那么计算机之间是如何进行通信的呢?这就不得不提到 TCP/IP 协议了。关于 TCP 协议的底层知识非常丰富,随便拎出来一点都能讲一整月。但在本篇文章中,我们只需要知道:
- TCP 是一种面向连接的可靠传输协议,能将大数据拆分成多个数据包传输。
- 每个数据包会经过 IP 层封装地址信息,安全送达接收端。
- 接收端会按照顺序还原这些数据包,还原出完整的数据。
如果这些技术细节你仍然觉得抽象,可以简单理解为:我们是通过网络将二进制数据发送出去,然后接收方根据约定的协议进行还原。
本篇文章将逐步带你了解通信协议的基础、主流服务调用实现方案,以及如何构建自定义协议。
二、通信协议
2.1 TCP 协议
TCP(Transmission Control Protocol)是传输层协议,提供可靠、有序、面向连接的数据传输能力。
- 三次握手:建立连接之前,客户端与服务端通过三次握手建立连接。
- 粘包与拆包:多个数据包可能被粘连在一起发送,接收端需解析边界。
- 流式传输:TCP 是字节流协议,必须由上层协议决定如何分割数据。
2.2 HTTP 协议
HTTP 是基于 TCP 的应用层协议,具备以下特点:
- 无状态,每次请求之间彼此独立。
- 文本传输,基于请求头、响应头和正文。
- 应用广泛,如浏览器请求、RESTful 接口调用。
常用的 HTTP 方法包括 GET、POST、PUT、DELETE 等。
2.3 RMI 协议
RMI(Remote Method Invocation)是 Java 提供的一种远程调用协议:
- 允许调用远程 Java 对象的方法。
- 底层依赖 TCP 和 Java 序列化。
- 使用 Stub(客户端代理)和 Skeleton(服务端代理)进行通信。
其主要局限性是只能用于 Java 应用之间的通信。
2.4 协议对比
| 协议 | 所属层 | 类型 | 特点 | 是否跨语言 |
|---|---|---|---|---|
| TCP | 传输层 | 二进制 | 可靠传输、无边界 | 是 |
| HTTP | 应用层 | 文本 | 简单、通用、无状态 | 是 |
| RMI | 应用层 | Java 对象 | 强封装、只适配 Java | 否 |
三、服务调用方案
3.1 Spring Cloud 方案
Spring Cloud 提供了基于 HTTP 协议的微服务通信解决方案:
- 使用 Feign 实现声明式调用。
- 配合 Eureka、Gateway、Config 等组件实现注册、路由、配置中心。
- 通常使用 JSON 序列化方式。
优点: 上手快、生态成熟、适合企业微服务项目。
3.2 Dubbo 方案
Dubbo 是阿里开源的高性能 RPC 框架:
- 默认使用 Netty + 自定义 Dubbo 协议(基于 TCP)。
- 支持多协议、多序列化方式(如 Hessian、Kryo)。
- 提供服务注册、负载均衡、容错、降级等能力。
适合场景: 内网高性能服务调用、延迟敏感场景。
3.3 gRPC 方案
gRPC 是 Google 推出的高性能跨语言 RPC 框架:
- 基于 HTTP/2 协议,支持多路复用。
- 使用 Protocol Buffers(ProtoBuf)作为序列化格式,体积小、效率高。
- 支持双向流、客户端流、服务端流等通信方式。
适合场景: 跨语言调用、高并发微服务系统、移动端。
3.4 调用方案对比
| 方案 | 协议 | 序列化 | 是否跨语言 | 特点 |
|---|---|---|---|---|
| SpringCloud | HTTP | JSON | 是 | 简洁易用、兼容性好 |
| Dubbo | TCP | 多种(Hessian/Kryo) | 否 | 性能强、内网优选 |
| gRPC | HTTP/2 | ProtoBuf | 是 | 高性能、跨语言 |
四、知识扩展
4.1 自定义通信协议
实际开发中,如果框架无法满足业务需求,也可以自定义通信协议:
- 定义自己的数据包结构,如:
[包头][包长][类型][数据体][校验码] - 通过 TCP 发送/接收二进制流,并在应用层解析
- 适用于物联网、游戏、消息中间件等场景
4.2 什么是 RPC
RPC(Remote Procedure Call)即远程过程调用:
- 是对 TCP 通信的封装
- 隐藏了底层传输细节,让调用远程服务像调用本地方法一样
- 涉及协议设计、序列化、网络传输、连接池、负载均衡等模块
4.3 序列化技术简析
| 序列化方式 | 可读性 | 性能 | 跨语言 | 备注 |
|---|---|---|---|---|
| JSON | 高 | 中 | 是 | 人类可读,体积大 |
| XML | 高 | 低 | 是 | 冗余信息多 |
| ProtoBuf | 低 | 高 | 是 | 紧凑、二进制格式 |
| Hessian | 低 | 高 | 否 | Dubbo 默认使用之一 |
| Kryo | 低 | 极高 | 否 | Java 高性能方案 |
五、总结与思考
- 服务调用的本质是网络通信 + 序列化 + 协议约定。
- 选择合适的通信协议,取决于项目的语言、性能、维护需求。
- SpringCloud 简单易用,适合 HTTP 服务;Dubbo 高性能但局限 Java;gRPC 适用于高并发 + 多语言。
- 理解协议的设计思路,有助于你读懂源码,甚至自己设计轻量级协议。
如果你掌握了这些内容,下一步可以深入学习 Netty、协议栈解析、或是构建自己的 RPC 框架。