這是自己搭建直播服務器、開發直播平台系列的文章,前面兩篇文章分別為:

這篇文章是在上面多頻道輸入輸出和權限控制的基礎上進行的。

一、目標

1、實現直播狀態的更改:

直播狀態的更改主要是為了顯示,在前端刷新列表的時候,用於判斷那些直播間在直播,哪些不在。):

  • 用戶開始推流之后,操作數據庫,更改直播狀態,顯示直播間已經開始直播。
  • 用戶推流結束或者關閉軟件后,操作數據庫,更改直播狀態。

2、實現簡單的人數統計(暫用):

這里實現人數統計是基於數據庫的(rtmp-nginx-module本身是有一個模塊的,可以實現當前視頻流觀看人數的統計),這里只是簡單的實現自增和自減數據庫。

  • 用戶觀看打開頁面開始觀看直播,數據庫字段自增1
  • 用戶關閉頁面后,連接斷掉,數據庫字段自減1

二、rtmp服務器的配置

在 實現nginx-rtmp-module多頻道輸入輸出與權限控制 這篇文章里,我們配置了 on_publish 這個參數。

主要實現多頻道和權限控制,用戶在正式推流到服務器之前首先去配置的url中驗證一下權限(具體的可以看上篇文章)。

目前我們需要配置更多的參數:

    application myapp{ live on; # live on表示開啟直播模式 on_publish http://192.168.124.125/on_publish.html; on_publish_done http://192.168.124.125/on_publish_done.html; on_play http://192.168.124.125/on_play.html; on_play_done http://192.168.124.125/on_play_done.html; }

可以看到,除了 on_publish ,我們還配置了 on_publish_done、on_play、on_play_done 三個參數,后面也是一個url。

這三個參數也是非常容易理解的,分別對應如下:

  • on_publish_done —— 推流結束
  • on_play —— 客戶端播放
  • on_play_done —— 客戶端播放結束

對上面三個參數的具體解釋和用法可以看rtmp的文檔:

r.jpg

經過上面的配置,用戶推送或者推送結束、或者用戶播放和播放結束都能夠觸發URL,同時操作數據庫即可。

三、程序部分注意問題

配置好了URL,就需要進行操作,但是會發現一個問題:

  • 不知道用戶觀看的是哪個流、或者不知道推送結束的是哪個流

上面問題可以看 實現nginx-rtmp-module多頻道輸入輸出與權限控制 這篇文章里面接收的 name參數 ,上面的配置中所有的推送都會攜帶一個name參數,而這個name是不可變的,用於標識當前流名稱。

用我寫的簡單舉個例子:

  • 下面是基於thinkphp5框架寫的。
  • url與函數不匹配是因為我做了route。

可以看到,每次的操作都會獲得一個name的參數,當然,除了name之外每個不同的配置有不同的參數可以獲取,具體可以去 文檔 了解一下

    /** * 用戶直播結束的回調事件 * - 用戶直播結束后,將status設置成0,標注該房間未在推流 * @param Request $request */ function onPublishDone(Request $request){ // 獲得stream name $name=trim($request->param('name')); // 關閉直播 設置status 為 0 Db::name('room')->where(['guid'=>$name])->setField('status',0); return json('')->code(200)->header(['關閉直播']); } /** * 用戶觀看直播的回調事件 */ function onPlay(Request $request){ // 獲得視頻流地址 $name=trim($request->param('name')); // 有人加入觀看,設置people +1 Db::name('room')->where(['guid'=>$name])->setInc('people'); } /** * 用戶結束觀看直播的回調事件 * @param Request $request */ function onPlayDone(Request $request){ // 獲得視頻流地址 $name=trim($request->param('name')); // 有人加入觀看,設置people -1 Db::name('room')->where(['guid'=>$name])->setDec('people'); }