当存在一个推流客户端正在向rtmp://xxx.com/live/yyy推流时,又有另一个推流客户端同时对这个地址进行推流,会发生什么呢?html
查阅了 Adobe RTMP Spec 发现规范自己并未说明和定义这个场景下RTMP服务器应该怎么处理。服务器
最近在实际工做中遇到部分客户对推流地址资源管理不恰当而致使重复推流报错的问题,且在查问题的过程当中发现各个CDN厂商对“抢流”的处理各不相同,查阅相关文档说明发现资料甚少,故专门对它们的抢流行为作以下分析。tcp
抢流:指对同个地址资源进行重复推流阿里云
tcp && tcp.port == 1935
(之因此不直接写rtmpt
是由于还想观察传输层的行为)rtmp://xxx.com/live/yyy
ffmpeg
推送一个本地电影文件:ffmpeg -re -i Movie-1.flv -vcodec h264 -f flv "rtmp://xxx.com/live/yyy"
ffmpeg
推送另外一个本地电影文件到同个URL:ffmpeg -re -i Movie-2.flv -vcodec h264 -f flv "rtmp://xxx.com/live/yyy"
ffplay
播放拉流地址内容注:下列结果仅表明发表本文的时候的各CDN厂家行为,随着厂商对服务器的更新迭代,可能会有所改变。code
厂商 | 现象 | 结论 | 官方文档说明 | 与文档描述一致 |
---|---|---|---|---|
网宿 | 二次推流报错,ffplay 拉流播放的是Movie-1内容 |
抓包分析发现第二次推流的RTMP链接能握手成功,可是publish() 请求发出以后服务器应答onStatus('NetStream.Publish.BadName') (见参考文档) |
直播推流与拉流 | ✔️ |
阿里云 | 二次推流报错,ffplay 拉流播放的是Movie-1内容 |
抓包分析发现第二次推流的RTMP链接能握手成功,可是推流几秒以后CDN服务器会发来TCP RST包强制断开RTMP的TCP链接 | 未找到 | ❓ |
腾讯云 | 二次推流成功,ffplay 拉流播放的是Movie-1内容关闭第一个推流的程序,播放内容变成Movie-2的内容 |
官方文档代表会拒绝第二个推流请求,可是实际实验下来居然是能够重复推且不报错,不知道腾讯云这么实现有没有其余用意 | 推流失败问题排查 | ❌ |
七牛云 | 二次推流报错,ffplay 拉流播放的是Movie-1内容 |
RTMP能握手成功,可是推流几秒以后服务器会发来TCP RST包强制断开RTMP的TCP链接 与官方文档中提到的后者挤掉前者的说法不一致 |
推流不成功的缘由和解决方法 | ❌ |
金山云 | 二次推流报错,ffplay 拉流播放的是Movie-1内容 |
抓包分析发现第二次推流的RTMP链接能握手成功,可是publish() 请求发出以后服务器应答onStatus('NetStream.Publish.AlreadyExistStreamName') (见参考文档) |
推拉流接入 | ✔️ |
总的来讲,按当前实验结果来看,在这种细枝末节的功能点上,金山云的文档说明最清晰最规范,点个赞!orm
网宿的行为符合Flash AS3
的定义,至少有据可依。htm
而腾讯云与七牛云的文档说明均存在错误的地方(至少本次实验中是这样的),尤为是腾讯云的现象让我很意外。ip
而阿里云居然连这块的文档都没有。。(也许是我没搜到,如有的话望指正)资源