1. 先搞清楚:RTSP 到底是干什么的
RTSP 这个协议,几乎所有做流媒体的人都接触过,但很多人对它的理解停留在"能拉流播放"这个层面。我第一次在项目里往死里调 RTSP 的时候,被它折磨得不轻:明明 ffmpeg 能拉流,换成自己的播放器就黑屏;OPTIONS 请求通了,DESCRIBE 却一直 401;SETUP 报 All Ports In Use,日志里却没有明确提示……后来把协议栈彻底梳理了一遍,才发现大部分问题都源于同一个误解——把 RTSP 当成一个"传输协议"来用。
1.1 它不是一个"传输视频"的协议
RTSP(Real Time Streaming Protocol,实时流传输协议)由 RFC 2326 定义,2014 年又有 RFC 7826 做了更新。它跑在 TCP 或 UDP 之上,默认端口 554,本质上是一个带状态的应用层控制协议,类似于多媒体界的"遥控器"。
这个"遥控器"负责什么呢?它负责协商会话参数、发起播放、暂停、快进、停止这些操作指令,但真正的音视频数据不经过 RTSP 传输,而是由 RTSP 会话协商出来的 RTP/RTCP 数据流承载。RTP(Real-time Transport Protocol)负责实际搬运音视频包,RTCP 负责传输统计和质量反馈,它们默认走 UDP 端口,通常是 5004、5006 这类偶数位端口。
用个最直白的类比:RTSP 是餐厅里的服务员,你通过服务员点餐、催菜、买单;RTP 是后厨传菜通道,菜从通道直接端到你桌上。服务员身上不端菜,但不代表服务员不重要——没有他把菜名传进后厨,后厨根本不知道你要吃什么。
所以排查 RTSP 问题时,第一反应不应该盯着"数据流为什么断",而是先确认"控制面协商是否成功"。控制面都谈崩了,数据面根本不会开始。
1.2 RTSP 解决的真实场景
RTSP 设计之初就面向**"点播 + 直播 + 控制"**三类需求:
- 点播(VoD):用户可以对流执行播放、暂停、恢复、seek 到任意时间点,这要求协议天然支持状态管理。
- 直播(Live):摄像头、编码器实时推流,客户端可以随时加入,从当前时间点开始接收。
- 多端同步:通过 RTSP 会话描述(SDP)把音频轨、视频轨、字幕轨等描述清楚,客户端可以按需 SETUP 不同的轨道。
这也解释了为什么安防监控、IP Camera、视频编码器、车载 DVR 几乎清一色支持 RTSP:因为这些设备的核心场景是"局域网内低延迟实时取流",RTSP 在这条赛道上积累了二十多年兼容性,VLC、FFmpeg、GStreamer、各种播放器 SDK 全都默认支持它。
提示:另一个真实场景是"多路并发控制"。一个媒体服务器可以同时维护大量 RTSP 会话,每个会话独立状态机,这对大规模监控平台的并发接入(比如一台 NVR 接入几十上百路摄像头)非常关键。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 一次完整 RTSP 会话:从 OPTIONS 到 TEARDOWN
抓包看一次完整的 RTSP 交互,你会发现整个流程特别像一个"状态机握手剧本",每一句对话都有明确的目的和顺序。理解了这个剧本,你才能在任何一步失败时快速定位问题。
2.1 五步握手:控制面的状态机
一次最基本的 RTSP 拉流过程长这样:
code复制C -> S: OPTIONS rtsp://192.168.1.64:554/stream1 RTSP/1.0
S -> C: RTSP/1.0 200 OK
Public: DESCRIBE, SETUP, TEARDOWN, PLAY, PAUSE, GET_PARAMETER, SET_PARAMETER
C -> S: DESCRIBE rtsp://192.168.1.64:554/stream1 RTSP/1.0
S -> C: RTSP/1.0 200 OK
Content-Type: application/sdp
(这里就是SDP报文内容)
C -> S: SETUP rtsp://192.168.1.64:554/stream1/track1 RTSP/1.0
Transport: RTP/AVP/UDP;unicast;client_port=6000-6001
S -> C: RTSP/1.0 200 OK
Transport: RTP/AVP/UDP;unicast;client_port=6000-6001;server_port=5004-5005
C -> S: PLAY rtsp://192.168.1.64:554/stream1 RTSP/1.0
S -> C: RTSP/1.0 200 OK
RTP-Info: url=rtsp://.../track1;seq=58874;rtptime=1820395125
C -> S: TEARDOWN rtsp://192.168.1.64:554/stream1 RTSP/1.0
S -> C: RTSP/1.0 200 OK
把这五步拆开看:
- OPTIONS 是客户端向服务器"打招呼",同时探测服务器支持哪些方法。有些摄像头不会把所有方法都在 Public 里列全,但 DESCRIBE 和 SETUP 一定会支持。
- DESCRIBE 是客户端向服务器要"菜谱",也就是 SDP 会话描述。服务器返回音视频轨道的编码格式、分辨率、帧率、采样率、SPS/PPS 等关键参数。
- SETUP 是为某个轨道建立传输通道。这里要指定传输模式是走 UDP 还是 TCP,客户端用哪个端口收 RTP 数据。有多少路轨道就发多少次 SETUP,视频轨和音频轨通常是两次独立的 SETUP。
- PLAY 是真正开始播放的指令,服务器收到后开始往客户端推 RTP 数据。
- TEARDOWN 结束会话,撤销所有通过 SETUP 建立的通道。
理解这个流程,很多问题就迎刃而解了。比如你在代码里只发了 OPTIONS 和 DESCRIBE 就等着收数据,那肯定等不到;再比如你发了 SETUP 但没收到 200 OK,就去解析 RTP 数据,当然是
