素材巴巴 > 程序开发 >

Nginx rtmp 点播流程

程序开发 2023-09-10 23:53:00

系列文章: 

Nginx rtmp 推流(publish) 解析_fdsafwagdagadg6576的专栏-CSDN博客
Nginx rtmp 拉流播放(play)_fdsafwagdagadg6576的专栏-CSDN博客
Nginx rtmp 拉流(转发pull)_fdsafwagdagadg6576的专栏-CSDN博客
Nginx rtmp 转推_fdsafwagdagadg6576的专栏-CSDN博客
Nginx rtmp 点播流程_fdsafwagdagadg6576的专栏-CSDN博客

直播场景涉及relay,live 模块,点播使用play模块 

1 模块设置

static ngx_command_t  ngx_rtmp_play_commands[] = {
 //一项为 "play",点播业务的nginx.conf中,就配置了该命令.因此先看该模块是如何解析 play 配置项的:{ ngx_string("play"),NGX_RTMP_MAIN_CONF|NGX_RTMP_SRV_CONF|NGX_RTMP_APP_CONF|NGX_CONF_1MORE,ngx_rtmp_play_url,NGX_RTMP_APP_CONF_OFFSET,0,NULL },......
 }

点播模块入口是ngx_rtmp_play_url

2 流程图:

上图是点播的整个信令交互流程.下面是audio,video数据流发送过程.

3 audio,video 发送

点播可以播放mp4,flv两种格式。可以播放本地和网络两种路径文件.
本例以播放本地flv文件为例:
3.1  初始化

3.2 发送流程图

先发送metadata,后发送audio,video数据。
ngx_rtmp_play_send 是点播发送的核心函数(直播是ngx_rtmp_live_av).

发送的核心是循环调用ngx_rtmp_play_send,读取一个flv文件tag,发送一个,然后再读取再发送,直到发送全部完成。

 3.3 seek

绿色发送接口即3.2

4 源码分析

//点播的最后一个调用就是在该函数中循环的,直到全部发送文件完成后,才返回.
 static void//发送给player
 ngx_rtmp_play_send(ngx_event_t *e)
 {...ctx = ngx_rtmp_get_module_ctx(s, ngx_rtmp_play_module);ts = 0;//==1调用flv,mp4封装的send函数(ngx_rtmp_flv_send,ngx_rtmp_mp4_send).时间戳是在那里设置的rc = ctx->fmt->send(s, &ctx->file, &ts);......if (rc == NGX_OK) {//===2 每发送完成一次,就将其放入到 ngx_posted_events 延迟队列中====
 然后由下一次 ngx_process_events_and_timers 函数中的循环调用到它 */ngx_post_event(e, &ngx_posted_events);return;}//===3 end====ngx_rtmp_send_stream_eof(s, NGX_RTMP_MSID);ngx_rtmp_send_play_status(s, "NetStream.Play.Complete", "status", ts, 0);ngx_rtmp_send_status(s, "NetStream.Play.Stop", "status", "Stopped");
 }
ngx_process_events_and_timers(ngx_cycle_t *cycle)
 {ngx_event_process_posted(cycle, &ngx_posted_accept_events);....
 }
 void //就是遍历event的队列,调用event的handler函数。
 ngx_event_process_posted(ngx_cycle_t *cycle, ngx_queue_t *posted)
 {ngx_queue_t  *q;ngx_event_t  *ev;while (!ngx_queue_empty(posted)) {q = ngx_queue_head(posted);ev = ngx_queue_data(q, ngx_event_t, queue);ngx_delete_posted_event(ev);//添加accept or read handler callbackev->handler(ev);}
 }

流程:
1) ngx_read_file:按照flv tag 读取
2) ngx_rtmp_prepare_message: 按照rtmp协议打包
3) ngx_rtmp_send_message:发送rtmp audio,video
4 )  将发送事件放入event queue
5)  从queue中取出发送event ,执行handler(callback)函数ngx_rtmp_play_send 
上述流程实现了,循环读取发送flv 文件

读取mp4文件,需要了解Mp4格式。
读取网络路径文件,待续.

如果对您有所帮助,请随手点赞,谢谢


标签:

上一篇: Surface Normal Vector in OpenCascade 下一篇:
素材巴巴 Copyright © 2013-2021 http://www.sucaibaba.com/. Some Rights Reserved. 备案号:备案中。