ARTICLE · INTELLIGENCE

战地情报 · 详情页

来自尧图项目组的一线实战观察与深度解析

多品牌摄像机统一接入:基于GB28181/RTSP融合网关的架构与实践

多品牌摄像机统一接入:基于GB28181/RTSP融合网关的架构与实践 前年接手了一个让我印象很深的项目把某个单位分布在三个园区、分好几批采购、品牌型号完全不同的摄像机统一接到同一个视频平台里。设备清单拉出来一看有支持GB28181的有只给RTSP地址的还有那种只能靠私有SDK拉的。一开始团队也是常规思路挨个对接厂家SDK结果干了不到两周就发现这条路走不通——接口风格不同、文档不全、联调周期太长于是全盘推翻改走“基于GB28181/RTSP融合网关”的路线。这篇文章就是想把这个项目的完整方案梳理一遍多品牌设备如何通过融合网关统一接入、协议层落地时有哪些坑、边缘推流架构怎么搭、以及真实环境里遇到的那些排查实录。标题里说的“消融协议壁垒”本质上就是用一层网关把设备侧乱七八糟的协议统一成一套东西让上层平台只认一种设备模型。1. 项目背景与整体思路拆解1.1 多品牌设备接入的三大痛点做视频接入集成的人基本都被这三件事折磨过。第一是协议碎片化。同一个项目里不同厂商的设备对“接入”这件事的理解完全不一样。有的设备GB28181实现得很标准注册、目录、点播一次通过有的设备明明写着支持国标实际信令报文里少了字段、多了私有扩展甚至SDP里媒体描述写得不规范协商成功率全看运气。RTSP这边更乱各家对DESCRIBE/SETUP/PLAY的实现细节都有差异认证方式有Basic也有Digest传输模式有的只认UDP有的只认TCP。第二是SDK绑定的问题。很多老项目里的设备只支持厂家的私有SDK接入这意味着你要在平台侧集成多个厂商的SDK而且这些SDK通常只提供Windows的库或者特定的运行时环境部署起来非常受限。SDK依赖一旦升级或者接口有变化整个平台都要跟着改。第三是流出口的杂乱。设备侧能输出的流不外乎RTSP、GB28181的RTP/PS流、或者SDK回调出来的裸数据。可是业务侧要消费的是Web播放、手机播放、平台级联、录像存储这些消费端协议的诉求完全不一样。如果每个业务侧都直接去对接设备侧的协议那接一个业务就要做一次适配。1.2 方案选型为什么是融合网关而不是逐个适配SDK最初摆在台面上有两个方案。方案A是继续逐厂商接SDK把不同厂商的SDK封装成统一接口供上层调用。方案B是搭一层融合网关优先用GB28181/RTSP这类标准协议接入对实在不行的设备再用SDK兜底同时网关内部统一做设备建模和流媒体转换。最后选了方案B核心原因有三点。第一标准协议接入的维护成本远低于SDK。GB28181和RTSP都是公开的标准或事实标准不依赖任何一家厂商的私有库设备升级、替换时只要协议标准没变网关不用动。接SDK则意味着每新增一个品牌就要重新集成一个动态库编译、排错、测试一条龙周期按周算。第二网关天然是流媒体的汇聚点和转换层。设备侧只要是能输出标准RTP/PS流或者RTSP流的网关都能收。收到之后在网关内部转成统一的流媒体格式再对外提供WebRTC、HLS、HTTP-FLV这些出口。这个能力是单纯SDK集成做不到的。第三现场网络环境的适配更灵活。实际部署里设备常常分散在不同的NAT后面信令能通、媒体不一定通UDP推流会丢包、TCP推流延时高。网关可以在信令和媒体两个层面做地址改写和协议转译这是任何单一SDK都无法覆盖的。1.3 网关整体架构与各模块职责网关的架构按功能可以分为四层。接入层负责协议适配。这一层实现了GB28181的SIP UA作为SIP服务器接收设备注册实现了RTSP客户端去主动拉取设备流也预留了厂商SDK接入插件位。协议转换层做的是“统一语义”。不管设备是通过什么协议进来的进入网关后都会被转成统一的设备模型一个设备ID、一个通道ID、一路流地址统一协议差异只留在接入层内部。流媒体服务层负责收流、转码和分发。它从设备侧拉取原始流按需启动接收队列需要时做转码或转封装然后向不同的消费端输出。边缘推流控制层则负责会话管理。它决定什么时候拉流、拉到哪个边缘节点、向哪个方向的观看端推流以及会话空闲时什么时候回收。这套分层设计最大的好处是上层平台和下层设备完全解耦。平台加一个播放请求只需要跟网关的推流控制层打交道完全不用管底层是哪家的摄像机。2. 协议接入层GB28181与RTSP的落地实现2.1 GB28181接入的实现要点与信令细节GB28181的接入部分本质上是实现一个SIP服务器然后处理几类核心信令注册、心跳、目录、实时视音频点播。注册流程是这样的设备启动后向配置好的SIP服务器地址发送REGISTER请求。网关作为SIP服务器第一次收到REGISTER后返回401未授权并在响应里带上WWW-Authenticate摘要认证参数。设备收到401后重新发起REGISTER请求头里的Authorization携带用户名和加密后的密码。这里有个容易踩的坑用户名不是随意定的通常就是设备的国标编码密码的摘要计算如果不按标准来很多设备会一直报403。调试时一定要把SIP报文原文打出来对比。设备注册成功后会周期发送心跳Keepalive。网关端要用心跳来维护设备在线状态同时要允许设备和网关之间的心跳间隔存在波动。如果网关判断超时的阈值设得太紧网络抖动一下设备就会被误判离线。实时点播是整个接入过程中最麻烦的一环。平台侧要对某个通道发起播放时网关会向设备发送INVITE请求请求体的SDP里携带媒体接收地址、端口、媒体格式等信息。设备收到后返回200 OK里面带设备侧的媒体协商结果通常包含它准备发送媒体流的RTP端口。网关收到后发ACK设备这才开始向网关推流。实际项目里这个环节出现过很多问题。比如设备返回的SDP里媒体描述行的IP地址是内网地址跨公网时会出现媒体流根本推不到网关的问题再比如有些老设备不支持TCP承载RTP只接受UDP在公网丢包环境下画面会花斑一片。针对前者网关要在收到SDP后做地址改写判断必要时通过拓扑信息把接收地址替换成可达的外网地址针对后者要允许通过配置强制切换传输模式。2.2 RTSP设备的兼容接入处理RTSP设备接入相对直接但兼容性问题琐碎。核心流程就是OPTIONS确认能力、DESCRIBE拿SDP、SETUP选择传输方式、PLAY开始推流。DESCRIBE阶段最容易遇到的问题是SDP里的control字段不统一。有的设备给出的control是完整的URL有的只给出相对路径网关拼接时就要做判断。我习惯的做法是先尝试直接用完整的control字段如果失败再尝试用原始RTSP URL拼接这样成功率最高。认证方面RTSP设备有Basic和Digest两种。Basic就是把用户名密码做Base64安全性很差但很多老设备只有这种Digest相对好一些不过有些设备对Digest的算法实现不标准经常要试两三种方式才能通过认证。网关里要做一个认证重试的逻辑先按Basic发被拒了再用Digest。传输模式上UDP延迟低但是容易丢包TCP稳定但延时略高。在有公网转发和NAT的环境下我强烈建议优先强制走TCP否则视频花屏排查起来非常痛苦。网关的RTSP客户端在SETUP阶段要主动声明要TCP模式。部分设备对这个协商字段非常挑剔一旦发现它返回了非预期结果就直接断开重来不要纠结于信令层面的小问题。2.3 私有SDK与兜底接入策略标准协议接入得再好也总有漏网之鱼。一些很早的采买设备既没有GB28181选项RTSP地址又没开放这时绕不开SDK。我的建议是SDK接入一定要隔离在网关的接入层做成独立插件。不要为了某一个设备型号把SDK依赖污染到整个网关核心。插件只负责做三件事发现设备、返回流地址、控制信令。满足这三件事的抽象后面再加新品牌SDK都不至于伤筋动骨。在主流的方案之外还有一个低调但很实用的兜底思路很多设备虽然不开放SDK文档但通过ONVIF其实能拿到RTSP取流地址。我后来整理了一套自动探测流程网关对接入域做网络扫描发现ONVIF设备后自动拉取媒体地址能拿到就直接按RTSP接入绕开了SDK。这个办法在多品牌混合的项目里尤其管用接入量一下子就上来了。3. 统一设备模型与流媒体会话管理3.1 设备抽象模型与统一编码设计多协议接入的最终目标是让上层平台只面对一套设备模型。这套模型在我的实践里分为两层设备层和通道层。一个设备可以对应多个通道。设备层记录设备的厂商类别、接入协议类型、在线状态、SIP或RTSP地址等信息通道层对应一路视频记录通道编码、通道名称、视频编码格式、音频格式等。关键点是编码设计。GB28181本身有严格的设备编码规范统一编码有助跨域管理。我在接入设备时要求每台设备都被分配一个全局唯一的国标编码规则与标准保持统一区域中心、业务类型、设备序号等部分都按规范填。这样无论设备是GB28181注册进来的还是RTSP/ONVIF拉进来的在上层平台看来都是一个标准设备。审核这个编码环节不能省编码一旦乱后续级联向上级平台上报目录时会出各种怪问题。通道模型还需要记录“能力集”。云台能不能控制、有没有告警IO、有没有音频这些要尽早在接入阶段探测清楚。不要等到业务要开云台才发现设备根本没这个能力到那时候返工代价很高。3.2 目录管理、级联对接与状态同步GB28181的目录管理是接入环节里每天都在跑的动作。设备注册上线后可以选择主动上报目录也可以由网关发送目录查询请求去拉取。目录项里包含设备ID、通道ID、通道名称、状态、经纬度等。我建议都以设备主动上报为主网关做被动接收和增量更新这样能减少信令交互也避免有的设备对目录查询响应不及时。级联对接是另一个高频需求。当平台规模变大往往需要把网关的目录再上报到上一级的中心平台。这时网关的角色就从“接入网关”变成了“下级平台”要主动向中心SIP服务器注册再通过MESSAGE携带目录信息。更重要的是当上级平台发起播放时网关还要能把对设备侧的点播请求“翻译”过去。这条链路里SIP域的配置要非常小心Via字段、Contact字段、以及请求里的域标识都必须是上级平台能够识别的。稍有偏差上级平台可能一直显示下级平台离线。状态同步同样不能忽略。心跳超时、设备重启、网络断连、通道编码变化这些状态要及时更新到统一模型里再通过告警上报或者目录状态字段变更同步给上层平台。做不好状态同步平台上的在线状态就是一张永远不准确的值班表。4. 边缘推流架构从设备流到多端分发4.1 推流链路设计与为什么必须做边缘汇聚先看一个典型的业务链路Web端想看某路视频请求到了中心平台平台要拿到设备流然后转发给浏览器。如果中心平台直接去拉设备流再转发会有两个问题。第一是带宽汇聚问题。所有设备的码流都往中心节点涌100路4Mbps就是400Mbps的出口压力一旦并发上来中心节点先垮。第二是延迟问题。中心节点如果在地理位置上离设备很远跨运营商的链路叠加起来播放端看到的延迟指数级上升。边缘汇聚就是要把“拉流”这个动作下沉到离设备最近的边缘节点。边缘网关在本地把各品牌的设备流拉进来统一转成标准流后缓存在本地上层平台只要从边缘节点取流即可。如果某个片子整个区域都在看那中心平台的压力几乎为零因为流量在边缘已经消化掉了。从我实测的情况看边缘汇聚带来的改善非常明显。原来从中心转发一路公网流延时往往在1秒以上边缘直连后内网可以做到几百毫秒边缘到中心之间的带宽压力也大幅下降平时只有平台管理信令和必要的录像回传流量通过。4.2 转码、封装与低延迟输出方案设备出来的原始编码流常见的是H.264和H.265封装格式有裸流、PS流、RTSP流等。输出端口的格式则因播放端而异。Web端播放有两类主流选择。一类是HLS兼容性最好几乎所有浏览器和移动端都支持但切片机制天然带来5秒以上的延迟对视频监管类场景没问题对实时指挥调度类场景就不行。另一类是WebRTC和HTTP-FLV延迟可以压到很低。WebRTC端到端延迟能控制在500毫秒以下非常适合需要快速响应的业务HTTP-FLV在浏览器里需要走MSE扩展延迟约1到2秒。转码不是必选项但有几种情况必须转源流是H.265而播放端不支持H.265时要转成H.264原始码率太高、业务侧只需要低清晰度预览时要降码率和分辨率当设备输出的是老旧的MPEG-4时更是要转。我曾在一台带核显的边缘节点上实测过转码用硬件加速一路1080P H.265转H.264只占用很少的CPU但如果是纯软件转码一路就可能吃掉两个核。所以规划转码资源前一定要先分清楚哪些通道需要转码转码到什么规格用什么硬件做。别上来就把所有设备都默认转码那是给自己找麻烦。4.3 按需推流与会话回收策略边缘推流有个和传统直播完全不同的特点视频通道数量大但真正在看的并发很小。几十路设备里可能只有两三路有人在看。所以推流控制的核心原则是“按需拉流”。当有播放请求时才去设备侧拉流没有观看端时主动断开否则边缘节点会白白占着几十路带宽和设备连接。GB28181点播通道通常有并发限制一直挂着不释放其他请求就进不来了。按需拉流还需要快。某路设备没有流用户点开播放器时边缘网关要立刻发起拉流从发INVITE到收到第一帧画面设计目标应该在2秒以内。所以网关要维护一个“热连接池”对最近播放过的通道保持一个短时的缓存流超过比如5分钟没人看才释放。这样用户再次点开时可以直接命中缓存不用重新走设备侧的点播流程。会话回收策略也在此处互补。边缘网关要定期扫描推流会话的空闲时间超过阈值就主动断开设备侧拉流连接。这个阈值调得太短会导致用户反复点播时体验差调得太长又会浪费带宽一般取2到5分钟比较合适。5. 部署实测与参数调优记录5.1 部署拓扑、性能估算与硬件选型本项目里网关采用分布式部署三个园区各部署一台边缘节点节点上跑完整的接入和推流组件中心机房再部署一台中心网关节点负责级联上级平台和跨园区调度。边缘节点的硬件选型主要看路的并发数和是否转码。纯转发场景压力不大一台4核8G的机器带80路接入绰绰有余。如果带转码就要评估硬件加速能力我建议优先选带核显的CPU或者加一块低功耗的编码卡尽量避免软编。带宽估算公式可以很简单单路码率乘以上路数。以1080P主码流4Mbps为例100路全量并发拉流就是400Mbps。这个带宽在中心节点很可能撑不住所以在大规模场景里边缘节点要做好“主码流只对录像和重要业务开放预览优先用子码流”的策略把子码流的码率控制在1Mbps以内能显著降低对网络的压力。5.2 关键配置参数与实测数据一些参数在我的项目里是反复调整过的。SIP信令这块注册有效期设置和心跳超时阈值必须一起调。设备通常60秒发一次心跳我把离线判定阈值设在180秒给足了网络抖动缓冲。正常情况下在线率能维持在99%以上。流媒体接收这块接收缓存队列大小很关键。UDP推流时抖动大缓存队列设太短会导致花屏设太长又增加延迟。我在内网环境下把接收缓存设为512毫秒左右实测画面平滑度和延迟之间平衡得不错公网环境则适当加大到1秒以上。转码输出这块HLS切片时长设为4秒延迟实测在6到8秒HTTP-FLV和WebRTC这类低延迟协议内网端到端只用了约300到500毫秒。最影响用户体验的首屏时间优化后基本控制在2秒左右。5.3 参数调优清单把常用的调优点整理成一张清单方便直接照着做设备侧统一开启NTP时间同步很多协议鉴权校验依赖时间窗口设备时间不准会导致认证失败。信令侧SIP注册有效期默认3600秒心跳间隔与超时阈值按3倍原则配置。媒体侧尽量使用TCP承载RTP/RTSP公网可靠性高仅在内网可控环境使用UDP。网关侧为每个协议插件设置独立的日志级别排查时能按插件开关详细日志。推流侧按需拉流空闲回收时间设置在2到5分钟热缓存时间不要超过5分钟。安全侧只开放信令端口和媒体端口其余的设备管理端口不要暴露在外网。6. 常见问题与排查技巧实录6.1 高频问题速查表做这类项目百分之八十的时间都在处理下面几类问题。我把它们整理成速查表排查时可以对照着来。现象可能原因排查步骤设备一直不在线注册失败认证失败、密码特殊字符、时间不同步抓SIP报文看401/403核对密码散列算法校正设备时间设备在线但点播超时SDP协商失败、媒体端口不通、SSRC冲突看INVITE请求与200 OK的SDP比对确认RTP收流端口双向互通画面花屏、马赛克UDP丢包、接收缓存过小看丢包统计切换TCP承载加大接收缓存播放有画面无声音音频编码协商错误、采样率不匹配看SDP里的音频参数确认G.711/AAC协商结果开启音频转码兜底平台侧显示离线设备侧正常心跳超时阈值过小、网络对时不准看心跳间隔和超时阈值适当放大阈值部署对时部分通道老掉线设备固件异常、点播连接未释放查看通道侧日志检查拉流会话是否回收尝试重启设备验证6.2 避坑经验与排查工具建议有几条经验是常规文档里不会写的值得单独拿出来讲。第一日志要能完整记录SIP报文体。做GB28181接入看不到完整信令报文排查就是抓瞎。调试阶段网关里要把信令原文全部落盘并且支持按设备编码检索。有一次设备反复注册不成功我把注册报文打出来逐字段比对发现是这个厂家在URI里多拼了一个斜杠导致网关解析失败。这种问题不看报文根本定位不到。第二媒体端口放行要成段放行。RTP传输用的端口是动态协商出来的如果防火墙只开了一两个固定端口那专项点播必然失败。建议在网关侧收流端口配置成一个连续的区间比如9000到10000安全策略上放行这一段。第三设备兼容性测试要前置。不要等设备全部上线了再开始调。项目进场的第一天就应该把各种品牌的样机各拿一台在测试环境里跑一遍接入、点播、云台、告警的完整链路。所有兼容性问题在测试环境里先暴露现场的交付体验完全不一样。第四网关服务要有看门狗。现场经常出现设备侧异常流把网关进程拖死的情况。网关进程要支持崩溃自动拉起同时拉流会话要有失败重试机制重试到一定次数后要主动放弃并上报告警避免一直挂在坏通道上消耗系统资源。我在这个项目里收尾时还有一个体会协议壁垒这种东西短期看是技术问题长期看其实是架构问题。设备侧的拨测环境千差万别但只要网关这层把接入协议收敛好了平台侧永远是一套稳定接口。与其一遍遍适配不同厂家的“特色”不如一次性把网关做扎实。回头再看这个决定是整项目里最值的一笔投入。
RELATED READING

延伸阅读

更多一线实战笔记与深度复盘,助您持续精进