# ZMQ 协议详细总结


# ZeroMQ（ZMQ）协议详细总结
ZeroMQ（又称ØMQ/0MQ/ZMQ）是一款**高性能、异步、无中心化代理（Brokerless）** 的消息通信库，其底层基于标准化的**ZMTP（ZeroMQ Message Transport Protocol）** 传输协议实现，以嵌入式库的形式集成到应用程序中，屏蔽了底层网络通信、连接管理、队列调度、重连机制等复杂细节，通过统一的套接字API提供多种预置的通信模式，专为低延迟、高吞吐、松耦合的分布式系统设计。

## 一、核心定位与设计理念
1.  **无代理架构**：不同于RabbitMQ、Kafka等依赖中心化Broker的消息中间件，ZMQ无独立部署的服务进程，直接嵌入应用端到端通信，大幅降低架构复杂度与传输延迟。
2.  **消息导向而非字节流**：将TCP字节流抽象为离散的消息帧，开发者无需处理粘包、拆包问题，保证消息的原子性投递。
3.  **通信模式预置**：将通用分布式通信场景抽象为标准化的套接字配对模式，开发者无需手动设计通信拓扑，仅需选择匹配的模式即可快速搭建通信架构。
4.  **全场景传输抽象**：统一线程间、进程间、跨主机、跨网络的通信API，一套代码可无缝适配不同传输层级，仅需修改连接地址即可切换。

## 二、ZMTP核心传输协议规范
ZMTP是ZMQ的底层标准化传输协议，定义了对等节点之间消息交换的完整规则，最新**稳定版本为ZMTP 3.0**，最新草案版本为ZMTP 3.1（新增心跳、资源管理、扩展命令等能力），协议完全开源并遵循RFC标准化流程。

### 2.1 协议分层架构
ZMTP自下而上分为三层，各层职责清晰且解耦：
| 层级 | 核心职责 | 关键能力 |
|------|----------|----------|
| 组帧层（Framing Layer） | 将底层字节流转换为离散的帧，定义帧的编码格式 | 消息边界界定、长短帧适配、帧元数据标记 |
| 连接层（Connection Layer） | 管理连接生命周期，完成版本协商、安全握手、元数据交换 | 版本兼容、身份认证、加密传输、连接保活 |
| 内容层（Content Layer） | 基于套接字类型定义消息的路由、过滤、投递语义 | 消息模式匹配、订阅过滤、路由寻址、负载均衡 |

### 2.2 连接生命周期
一个完整的ZMTP连接分为三个核心阶段，严格按顺序执行：
```
连接 = 问候阶段（Greeting） → 握手阶段（Handshake） → 流量阶段（Traffic）
```

#### 1. 问候阶段（Greeting）
固定64字节长度，用于对等节点之间的版本协商与安全机制确认，是连接建立的首个步骤，格式如下：
| 字段 | 长度 | 说明 |
|------|------|------|
| 签名（Signature） | 10字节 | 固定格式：`0xFF + 8字节填充 + 0x7F`，用于标识ZMTP协议，避免与普通TCP流量混淆 |
| 版本（Version） | 2字节 | 主版本号+次版本号，ZMTP 3.0为`0x03 0x00`，3.1为`0x03 0x01`，支持向下兼容协商 |
| 安全机制（Mechanism） | 20字节 | ASCII字符串，不足补0x00，用于协商加密认证方式，核心支持`NULL`/`PLAIN`/`CURVE` |
| 服务端标识（as-server） | 1字节 | 0x00=客户端，0x01=服务端，用于安全握手的角色区分 |
| 填充位（Filler） | 31字节 | 固定补0x00，将问候帧补齐至64字节 |

版本协商规则：
- 节点必须接受高于自身的主版本号，保证向前兼容；
- 可通过前11字节检测旧版本协议，自动降级适配ZMTP 2.0/1.0；
- 若双方安全机制不匹配，必须立即关闭连接，防止降级攻击。

#### 2. 握手阶段（Handshake）
基于协商好的安全机制执行认证握手，由一个或多个命令帧组成，只有握手成功才能进入流量阶段。
- 核心命令：`READY`（就绪确认）、`ERROR`（错误终止）；
- 握手成功后，双方通过`READY`命令交换元数据，包括套接字类型、节点身份（Identity）、资源标识等；
- 若认证失败，发送`ERROR`命令并关闭连接，避免无效连接占用资源。

#### 3. 流量阶段（Traffic）
连接正式就绪，可双向混合传输**命令帧**与**消息帧**，是应用数据的核心传输阶段。
- 内置命令：`SUBSCRIBE/CANCEL`（订阅管理）、`PING/PONG`（心跳保活）、`JOIN/LEAVE`（组播组管理）等；
- 消息帧：承载应用层数据，保证原子性、有序性投递。

### 2.3 帧格式定义
ZMTP中所有数据均以**帧（Frame）** 为单位传输，分为命令帧和消息帧，支持短帧（0-255字节）和长帧（0-2^63-1字节）两种格式，适配不同大小的消息负载。

#### 帧的通用结构
```
帧 = 标志位（1字节） + 长度字段（1/8字节） + 帧体（长度字段指定的字节数）
```
1.  **标志位（Flags）**：1字节，按位定义帧的属性，核心位定义：
    | 位序号 | 名称 | 含义 |
    |--------|------|------|
    | Bit 0（最低位） | MORE | 后续还有帧，1=多部分消息的中间帧，0=消息最后一帧 |
    | Bit 1 | LONG | 长度字段格式，0=1字节短长度，1=8字节网络字节序长长度 |
    | Bit 2 | COMMAND | 帧类型，1=命令帧，0=消息帧 |
    | Bit 3-7 | 保留位 | 必须置0，用于未来扩展 |
2.  **长度字段**：不包含标志位和自身，仅标识帧体的字节长度；短帧用1字节，长帧用8字节大端序无符号整数。
3.  **帧体**：命令帧承载协议命令与参数，消息帧承载应用数据。

#### 关键规则
- **多部分消息**：一条完整的ZMTP消息可由1个或多个帧组成，除最后一帧外，所有帧的MORE标志位必须置1；消息保证原子性投递，要么全部帧送达，要么完全不送达。
- **命令帧约束**：命令帧必须为单帧，MORE标志位必须置0，帧体由命令名称+命令数据组成。

### 2.4 安全机制
ZMTP设计了可扩展的安全框架，内置三种核心安全机制，覆盖从无加密到全链路加密认证的场景，禁止非对称的安全机制协商，防止降级攻击：
1.  **NULL机制**：默认机制，无认证、无加密，明文传输，适用于可信内网环境，性能最高；握手仅需交换`READY`命令即可完成。
2.  **PLAIN机制**：明文用户名/密码认证，无传输加密，适用于内网身份校验场景，密码在网络中明文传输，公网环境需配合VPN使用。
3.  **CURVE机制**：基于Curve25519椭圆曲线算法的全链路加密与双向认证，提供端到端的机密性、完整性与身份防伪造，是公网环境的推荐安全方案。

## 三、ZMQ核心通信模式
ZMQ的核心价值在于将分布式通信场景抽象为标准化的**套接字配对模式**，不同套接字类型严格遵循预定义的消息路由、投递、负载均衡语义，仅允许兼容的套接字类型配对通信。

### 3.1 基础核心模式
#### 1. 请求-应答模式（REQ/REP）
- **配对规则**：REQ ↔ REP，严格的一问一答语义
- **核心语义**：REQ端（客户端）必须先发送请求，再等待应答；REP端（服务端）必须先接收请求，再发送应答，请求与应答严格成对出现；支持1个REP对应多个REQ客户端，请求自动负载均衡。
- **适用场景**：简单RPC调用、客户端-服务端同步交互、命令控制类场景。
- **限制**：REQ端一次只能发起一个请求，未收到应答前无法发送新请求；REP端一次只能处理一个请求，未回复前无法接收新请求。

#### 2. 发布-订阅模式（PUB/SUB）
- **配对规则**：PUB ↔ SUB，一对多广播语义
- **核心语义**：PUB端（发布者）向所有连接的SUB端（订阅者）广播消息，消息基于**前缀匹配**的主题过滤；SUB端需显式订阅主题（空字符串订阅所有消息），仅接收匹配的消息；消息单向流动，PUB不关心SUB是否接收，订阅前发布的消息会直接丢弃。
- **适用场景**：实时行情推送、日志分发、系统事件通知、状态同步广播。
- **扩展**：支持XPUB/XSUB套接字，可实现订阅状态的反向通知，适配代理转发场景。

#### 3. 推拉模式（PUSH/PULL）
- **配对规则**：PUSH ↔ PULL，单向流水线语义
- **核心语义**：PUSH端发送的消息会自动负载均衡到所有连接的PULL端，每条消息仅送达一个PULL端；支持多PUSH对应多PULL，实现分布式任务分发与结果汇聚，无状态、无重复投递。
- **适用场景**：分布式任务调度、并行数据处理、生产者-消费者模型、任务流水线。

#### 4. 独占结对模式（PAIR/PAIR）
- **配对规则**：PAIR ↔ PAIR，一对一专属双向通信
- **核心语义**：仅允许两个PAIR套接字建立连接，双向异步通信，无负载均衡、无过滤、无状态机约束，是最接近原生TCP的模式，支持全双工数据传输。
- **适用场景**：进程内多线程通信、双节点热备同步、专属双向数据通道。

### 3.2 高级扩展模式
针对复杂分布式架构，ZMQ提供了更灵活的高级套接字模式，可组合构建复杂的代理、路由、集群架构：
1.  **路由-经销商模式（ROUTER/DEALER）**：ROUTER可基于节点身份（Identity）精准路由消息，DEALER可实现异步并发请求分发，二者组合可构建REQ/REP模式的代理网关，突破原生REQ/REP的同步限制，支持高并发请求处理。
2.  **客户端-服务端模式（CLIENT/SERVER）**：线程安全的异步RPC模式，CLIENT端可并发发送请求，无需等待应答；SERVER端可并发处理请求并精准回复，适配高并发微服务RPC场景。
3.  **无线-接收模式（RADIO/DISH）**：替代PUB/SUB的新一代组播模式，基于**精确组名匹配**而非前缀匹配，支持更灵活的消息分组，避免前缀匹配的误命中问题。
4.  **散列-聚集模式（SCATTER/GATHER）**：线程安全的PUSH/PULL替代模式，优化了分布式任务分发的负载均衡策略，适配大规模并行计算场景。

## 四、核心传输协议支持
ZMQ对底层传输协议做了全场景封装，同一套API可无缝切换不同传输方式，仅需修改连接地址前缀即可：
| 传输类型 | 地址前缀 | 适用场景 | 核心特点 |
|----------|----------|----------|----------|
| 线程间通信 | inproc:// | 同一进程内多线程数据交互 | 零拷贝、超低延迟、无系统调用，基于内存队列实现 |
| 进程间通信 | ipc:// | 同一主机内跨进程通信 | 基于Unix域套接字（Linux/macOS）/命名管道（Windows），性能远高于TCP |
| 跨网络TCP | tcp:// | 跨主机、跨网络分布式通信 | 可靠传输、自动重连、NAT穿透支持，适配绝大多数广域网场景 |
| 可靠多播 | pgm:///epgm:// | 局域网内一对多广播通信 | 基于PGM可靠多播协议，epgm为UDP封装的PGM，适配交换机多播环境 |
| WebSocket | ws:///wss:// | 浏览器-服务端实时通信 | 兼容WebSocket标准，支持前端页面与后端ZMQ服务直接通信 |

## 五、核心特性与可靠性机制
### 5.1 核心性能特性
1.  **异步非阻塞IO**：基于epoll/kqueue/iocp多路复用IO模型，事件驱动架构，单线程可支持数万并发连接，高并发场景下延迟可稳定在微秒级。
2.  **零拷贝优化**：支持mmap、sendfile等零拷贝技术，大消息传输无需多次内存拷贝，大幅降低CPU占用与传输延迟。
3.  **智能内存管理**：内置内存池与消息引用计数，避免频繁内存分配释放，小消息场景下性能优势显著。
4.  **高水位线（HWM）控制**：为每个套接字设置发送/接收队列的最大长度，防止消息堆积导致内存溢出，超过阈值后根据模式执行丢弃或阻塞策略。

### 5.2 可靠性保障机制
1.  **自动重连机制**：节点断开连接后，ZMQ会自动按指数退避策略尝试重连，无需开发者手动处理断连逻辑，网络恢复后自动恢复通信。
2.  **原子消息投递**：多帧消息保证全量或零投递，不会出现消息分片送达的情况，避免业务层处理不完整消息。
3.  **有序传输**：两个对等节点之间的消息，严格按照发送顺序投递，不会出现乱序问题。
4.  **心跳保活机制**：ZMTP 3.1内置`PING/PONG`心跳命令，可检测僵死连接、断网故障，超时后自动关闭连接并重连，避免无效连接占用资源。
5.  **离线消息缓存**：发送端会在内存队列中缓存未送达的消息（受HWM限制），对等节点重连后自动补发，短时间断网不会丢失消息（PUB/SUB模式默认不缓存订阅前消息）。

### 5.3 通用能力特性
1.  **跨语言/跨平台支持**：核心库由C++实现，提供C、C++、Python、Java、Go、C#等数十种语言绑定，支持Windows、Linux、macOS、嵌入式系统等全平台。
2.  **线程安全套接字**：提供CLIENT/SERVER、RADIO/DISH等线程安全套接字，可在多线程中直接调用，无需额外加锁，简化并发编程。
3.  **可扩展架构**：支持自定义安全机制、自定义传输协议，可根据业务需求扩展核心能力。
4.  **向下兼容**：ZMTP协议支持多版本协商，可与历史版本的ZMQ节点正常通信。

## 六、与传统消息中间件的核心差异
| 对比维度 | ZeroMQ | 传统消息中间件（RabbitMQ/Kafka） |
|----------|--------|------------------------------------|
| 架构模式 | 无中心化Broker，端到端嵌入式库 | 中心化Broker架构，依赖独立部署的服务节点 |
| 部署复杂度 | 极低，仅需集成库，无额外服务部署 | 高，需部署、运维Broker集群，配置容灾、扩容 |
| 核心定位 | 通信框架，专注于消息传输与模式抽象 | 消息中间件，专注于消息存储、持久化、消费管控 |
| 延迟性能 | 微秒级，端到端直传，无Broker转发开销 | 毫秒级，需经过Broker存储转发，链路更长 |
| 消息持久化 | 仅支持基础内存队列，无内置持久化 | 完善的磁盘持久化、消息回溯、死信队列机制 |
| 集群能力 | 需手动组合模式构建集群，无内置集群 | 原生支持集群、副本、主从、分区等高可用能力 |
| 适用场景 | 低延迟分布式通信、端到端数据交互、嵌入式系统 | 高可靠消息投递、业务解耦、流量削峰、日志存储 |

## 七、典型适用场景
1.  **高频交易系统**：金融行情推送、交易指令传输，依赖ZMQ的微秒级低延迟与高吞吐能力。
2.  **分布式实时计算**：任务并行分发、中间结果汇聚，基于PUSH/PULL模式构建数据处理流水线。
3.  **物联网/嵌入式系统**：边缘设备与云端的低资源占用通信，适配嵌入式设备的有限算力与内存。
4.  **微服务RPC框架**：基于REQ/REP或CLIENT/SERVER模式构建轻量级RPC通信层，替代重量级HTTP协议。
5.  **监控与日志系统**：基于PUB/SUB模式实现日志实时分发、监控指标广播，一对多高效传输。
6.  **多线程/多进程通信**：替代原生socket、共享内存，简化进程内/跨进程的异步通信开发。

## 八、常见使用注意事项
1.  **套接字配对严格性**：必须使用兼容的套接字类型配对，否则无法正常通信（如REQ不能直接与PULL配对）。
2.  **高水位线（HWM）配置**：必须根据业务场景设置合理的HWM，避免大流量场景下内存溢出；PUB/SUB模式下，慢订阅者会触发HWM，导致消息丢弃，需做好消费能力匹配。
3.  **消息持久化限制**：ZMQ无内置磁盘持久化能力，内存队列中的消息会在进程崩溃时丢失，需高可靠投递的场景需自行实现持久化与确认机制。
4.  **线程安全约束**：传统套接字（REQ/REP/PUB/SUB等）非线程安全，禁止多线程同时操作同一个套接字，需使用线程安全套接字或通过inproc模式做线程间通信。
5.  **订阅时机问题**：PUB/SUB模式下，SUB端晚连接会丢失订阅前的消息，需保证订阅先于发布，或通过REQ/REP模式做历史消息补全。
6.  **安全风险**：公网环境必须使用CURVE加密机制，禁止使用NULL/PLAIN机制明文传输，避免数据泄露与身份伪造。


