當存在一個推流客戶端正在向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
而阿里雲居然連這塊的文檔都沒有。。(也許是我沒搜到,如有的話望指正)資源