implemented on_publish_done, on_play_done; fixed repeated on_done

This commit is contained in:
Roman Arutyunyan 2012-09-06 16:10:21 +04:00
parent 4a775d6f0b
commit f221540a78

View file

@ -17,21 +17,29 @@ static ngx_rtmp_delete_stream_pt next_delete_stream;
static char *ngx_rtmp_notify_on_event(ngx_conf_t *cf, ngx_command_t *cmd, static char *ngx_rtmp_notify_on_event(ngx_conf_t *cf, ngx_command_t *cmd,
void *conf); void *conf);
static ngx_int_t ngx_rtmp_notify_postconfiguration(ngx_conf_t *cf); static ngx_int_t ngx_rtmp_notify_postconfiguration(ngx_conf_t *cf);
static void * ngx_rtmp_notify_create_app_conf(ngx_conf_t *cf); static void * ngx_rtmp_notify_create_app_conf(ngx_conf_t *cf);
static char * ngx_rtmp_notify_merge_app_conf(ngx_conf_t *cf, static char * ngx_rtmp_notify_merge_app_conf(ngx_conf_t *cf,
void *parent, void *child); void *parent, void *child);
static ngx_int_t ngx_rtmp_notify_done(ngx_rtmp_session_t *s, char *cbname,
ngx_url_t *url);
#define NGX_RTMP_NOTIFY_PUBLISHING 0x01
#define NGX_RTMP_NOTIFY_PLAYING 0x02
typedef struct { typedef struct {
ngx_url_t *publish_url; ngx_url_t *publish_url;
ngx_url_t *play_url; ngx_url_t *play_url;
ngx_url_t *publish_done_url;
ngx_url_t *play_done_url;
ngx_url_t *done_url; ngx_url_t *done_url;
} ngx_rtmp_notify_app_conf_t; } ngx_rtmp_notify_app_conf_t;
typedef struct { typedef struct {
ngx_uint_t flags;
u_char name[NGX_RTMP_MAX_NAME]; u_char name[NGX_RTMP_MAX_NAME];
u_char args[NGX_RTMP_MAX_ARGS]; u_char args[NGX_RTMP_MAX_ARGS];
} ngx_rtmp_notify_ctx_t; } ngx_rtmp_notify_ctx_t;
@ -53,6 +61,20 @@ static ngx_command_t ngx_rtmp_notify_commands[] = {
0, 0,
NULL }, NULL },
{ ngx_string("on_publish_done"),
NGX_RTMP_MAIN_CONF|NGX_RTMP_SRV_CONF|NGX_RTMP_APP_CONF|NGX_CONF_TAKE1,
ngx_rtmp_notify_on_event,
NGX_RTMP_APP_CONF_OFFSET,
0,
NULL },
{ ngx_string("on_play_done"),
NGX_RTMP_MAIN_CONF|NGX_RTMP_SRV_CONF|NGX_RTMP_APP_CONF|NGX_CONF_TAKE1,
ngx_rtmp_notify_on_event,
NGX_RTMP_APP_CONF_OFFSET,
0,
NULL },
{ ngx_string("on_done"), { ngx_string("on_done"),
NGX_RTMP_MAIN_CONF|NGX_RTMP_SRV_CONF|NGX_RTMP_APP_CONF|NGX_CONF_TAKE1, NGX_RTMP_MAIN_CONF|NGX_RTMP_SRV_CONF|NGX_RTMP_APP_CONF|NGX_CONF_TAKE1,
ngx_rtmp_notify_on_event, ngx_rtmp_notify_on_event,
@ -283,10 +305,12 @@ static ngx_chain_t *
ngx_rtmp_notify_done_create(ngx_rtmp_session_t *s, void *arg, ngx_rtmp_notify_done_create(ngx_rtmp_session_t *s, void *arg,
ngx_pool_t *pool) ngx_pool_t *pool)
{ {
u_char *cbname = arg;
ngx_rtmp_notify_app_conf_t *nacf; ngx_rtmp_notify_app_conf_t *nacf;
ngx_chain_t *hl, *cl, *pl; ngx_chain_t *hl, *cl, *pl;
ngx_buf_t *b; ngx_buf_t *b;
size_t name_len, args_len; size_t cbname_len, name_len, args_len;
ngx_str_t *addr_text; ngx_str_t *addr_text;
ngx_rtmp_notify_ctx_t *ctx; ngx_rtmp_notify_ctx_t *ctx;
@ -306,12 +330,13 @@ ngx_rtmp_notify_done_create(ngx_rtmp_session_t *s, void *arg,
return NULL; return NULL;
} }
cbname_len = ngx_strlen(cbname);
name_len = ctx ? ngx_strlen(ctx->name) : 0; name_len = ctx ? ngx_strlen(ctx->name) : 0;
args_len = ctx ? ngx_strlen(ctx->args) : 0; args_len = ctx ? ngx_strlen(ctx->args) : 0;
addr_text = &s->connection->addr_text; addr_text = &s->connection->addr_text;
b = ngx_create_temp_buf(pool, b = ngx_create_temp_buf(pool,
sizeof("&call=done") + sizeof("&call=") + cbname_len +
sizeof("&addr=") + addr_text->len + sizeof("&addr=") + addr_text->len +
sizeof("&name=") + name_len * 3 sizeof("&name=") + name_len * 3
+ 1 + args_len); + 1 + args_len);
@ -417,22 +442,37 @@ ngx_rtmp_notify_play_handle(ngx_rtmp_session_t *s,
static void static void
ngx_rtmp_notify_save_name_args(ngx_rtmp_session_t *s, ngx_rtmp_notify_init(ngx_rtmp_session_t *s,
u_char name[NGX_RTMP_MAX_NAME], u_char args[NGX_RTMP_MAX_ARGS]) u_char name[NGX_RTMP_MAX_NAME], u_char args[NGX_RTMP_MAX_ARGS],
ngx_uint_t flags)
{ {
ngx_rtmp_notify_ctx_t *ctx; ngx_rtmp_notify_ctx_t *ctx;
ngx_rtmp_notify_app_conf_t *nacf;
nacf = ngx_rtmp_get_module_app_conf(s, ngx_rtmp_notify_module);
if (nacf->done_url == NULL &&
nacf->play_done_url == NULL &&
nacf->publish_done_url == NULL)
{
return;
}
ctx = ngx_rtmp_get_module_ctx(s, ngx_rtmp_notify_module); ctx = ngx_rtmp_get_module_ctx(s, ngx_rtmp_notify_module);
if (ctx == NULL) { if (ctx == NULL) {
ctx = ngx_pcalloc(s->connection->pool, sizeof(ngx_rtmp_notify_ctx_t)); ctx = ngx_pcalloc(s->connection->pool, sizeof(ngx_rtmp_notify_ctx_t));
if (ctx == NULL) { if (ctx == NULL) {
return; return;
} }
ngx_rtmp_set_ctx(s, ctx, ngx_rtmp_notify_module); ngx_rtmp_set_ctx(s, ctx, ngx_rtmp_notify_module);
} }
ngx_memcpy(ctx->name, name, NGX_RTMP_MAX_NAME); ngx_memcpy(ctx->name, name, NGX_RTMP_MAX_NAME);
ngx_memcpy(ctx->args, args, NGX_RTMP_MAX_ARGS); ngx_memcpy(ctx->args, args, NGX_RTMP_MAX_ARGS);
ctx->flags |= flags;
} }
@ -447,19 +487,22 @@ ngx_rtmp_notify_publish(ngx_rtmp_session_t *s, ngx_rtmp_publish_t *v)
} }
nacf = ngx_rtmp_get_module_app_conf(s, ngx_rtmp_notify_module); nacf = ngx_rtmp_get_module_app_conf(s, ngx_rtmp_notify_module);
if (nacf == NULL) { if (nacf == NULL) {
goto next; goto next;
} }
if (nacf->done_url) { ngx_rtmp_notify_init(s, v->name, v->args, NGX_RTMP_NOTIFY_PUBLISHING);
ngx_rtmp_notify_save_name_args(s, v->name, v->args);
}
if (nacf->publish_url == NULL) { if (nacf->publish_url == NULL) {
goto next; goto next;
} }
ngx_log_debug1(NGX_LOG_DEBUG_RTMP, s->connection->log, 0,
"notify: publish '%V'", &nacf->publish_url->url);
ngx_memzero(&ci, sizeof(ci)); ngx_memzero(&ci, sizeof(ci));
ci.url = nacf->publish_url; ci.url = nacf->publish_url;
ci.create = ngx_rtmp_notify_publish_create; ci.create = ngx_rtmp_notify_publish_create;
ci.handle = ngx_rtmp_notify_publish_handle; ci.handle = ngx_rtmp_notify_publish_handle;
@ -480,19 +523,22 @@ ngx_rtmp_notify_play(ngx_rtmp_session_t *s, ngx_rtmp_play_t *v)
ngx_rtmp_netcall_init_t ci; ngx_rtmp_netcall_init_t ci;
nacf = ngx_rtmp_get_module_app_conf(s, ngx_rtmp_notify_module); nacf = ngx_rtmp_get_module_app_conf(s, ngx_rtmp_notify_module);
if (nacf == NULL) { if (nacf == NULL) {
goto next; goto next;
} }
if (nacf->done_url) { ngx_rtmp_notify_init(s, v->name, v->args, NGX_RTMP_NOTIFY_PLAYING);
ngx_rtmp_notify_save_name_args(s, v->name, v->args);
}
if (nacf->play_url == NULL) { if (nacf->play_url == NULL) {
goto next; goto next;
} }
ngx_log_debug1(NGX_LOG_DEBUG_RTMP, s->connection->log, 0,
"notify: play '%V'", &nacf->play_url->url);
ngx_memzero(&ci, sizeof(ci)); ngx_memzero(&ci, sizeof(ci));
ci.url = nacf->play_url; ci.url = nacf->play_url;
ci.create = ngx_rtmp_notify_play_create; ci.create = ngx_rtmp_notify_play_create;
ci.handle = ngx_rtmp_notify_play_handle; ci.handle = ngx_rtmp_notify_play_handle;
@ -510,32 +556,65 @@ static ngx_int_t
ngx_rtmp_notify_delete_stream(ngx_rtmp_session_t *s, ngx_rtmp_delete_stream_t ngx_rtmp_notify_delete_stream(ngx_rtmp_session_t *s, ngx_rtmp_delete_stream_t
*v) *v)
{ {
ngx_rtmp_notify_ctx_t *ctx;
ngx_rtmp_notify_app_conf_t *nacf; ngx_rtmp_notify_app_conf_t *nacf;
ngx_rtmp_netcall_init_t ci;
nacf = ngx_rtmp_get_module_app_conf(s, ngx_rtmp_notify_module); ctx = ngx_rtmp_get_module_ctx(s, ngx_rtmp_notify_module);
if (nacf == NULL || nacf->done_url == NULL) {
if (ctx == NULL) {
goto next; goto next;
} }
ngx_memzero(&ci, sizeof(ci)); nacf = ngx_rtmp_get_module_app_conf(s, ngx_rtmp_notify_module);
ci.url = nacf->done_url;
ci.create = ngx_rtmp_notify_done_create;
ngx_rtmp_netcall_create(s, &ci); if (nacf == NULL) {
goto next;
}
if (nacf->publish_done_url && (ctx->flags & NGX_RTMP_NOTIFY_PUBLISHING)) {
ngx_rtmp_notify_done(s, "publish_done", nacf->publish_done_url);
}
if (nacf->play_done_url && (ctx->flags & NGX_RTMP_NOTIFY_PLAYING)) {
ngx_rtmp_notify_done(s, "play_done", nacf->play_done_url);
}
if (nacf->done_url && ctx->flags) {
ngx_rtmp_notify_done(s, "done", nacf->done_url);
}
ctx->flags = 0;
next: next:
return next_delete_stream(s, v); return next_delete_stream(s, v);
} }
static ngx_int_t
ngx_rtmp_notify_done(ngx_rtmp_session_t *s, char *cbname, ngx_url_t *url)
{
ngx_rtmp_netcall_init_t ci;
ngx_log_debug2(NGX_LOG_DEBUG_RTMP, s->connection->log, 0,
"notify: %s '%V'", cbname, &url->url);
ngx_memzero(&ci, sizeof(ci));
ci.url = url;
ci.arg = cbname;
ci.create = ngx_rtmp_notify_done_create;
return ngx_rtmp_netcall_create(s, &ci);
}
static char * static char *
ngx_rtmp_notify_on_event(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) ngx_rtmp_notify_on_event(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
{ {
ngx_rtmp_notify_app_conf_t *nacf; ngx_rtmp_notify_app_conf_t *nacf;
ngx_str_t *url, *name; ngx_str_t *url, *name;
ngx_url_t *u; ngx_url_t *u;
size_t add; size_t add, len;
ngx_str_t *value; ngx_str_t *value;
value = cf->args->elts; value = cf->args->elts;
@ -568,13 +647,26 @@ ngx_rtmp_notify_on_event(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
nacf = ngx_rtmp_conf_get_module_app_conf(cf, ngx_rtmp_notify_module); nacf = ngx_rtmp_conf_get_module_app_conf(cf, ngx_rtmp_notify_module);
len = name->len;
switch (name->data[4]) { switch (name->data[4]) {
case 'l': /* on_pLay */
nacf->play_url = u; case 'l': /* on_pLay... */
if (len == sizeof("on_play") - 1) {
nacf->play_url = u;
} else {
nacf->play_done_url = u;
}
break; break;
case 'u': /* on_pUblish */
nacf->publish_url = u; case 'u': /* on_pUblish... */
if (len == sizeof("on_publish") - 1) {
nacf->publish_url = u;
} else {
nacf->publish_done_url = u;
}
break; break;
case 'o': /* on_dOne */ case 'o': /* on_dOne */
nacf->done_url = u; nacf->done_url = u;
} }