所以我使用以下方式设置了一个 nginx RTMP 服务器这个 rtmp 模块。下面是我按照以下方法创建的 nginx.conf本指南。
rtmp {
server {
listen 1935;
chunk_size 4096;
application live {
live on;
record off;
}
application movie {
live on;
record off;
exec ffmpeg -i rtmp://localhost:1935/movie -async 1 -vsync -1
-c:v libx264 -c:a libvo_aacenc -b:v 256k -b:a 32k -vf "scale=480:trunc(ow/a/2)*2" -tune zerolatency -preset veryfast -crf 23 -f flv rtmp://localhost:1935/hls/movie_low
-c:v libx264 -c:a libvo_aacenc -b:v 768k -b:a 96k -vf "scale=720:trunc(ow/a/2)*2" -tune zerolatency -preset veryfast -crf 23 -f flv rtmp://localhost:1935/hls/movie_mid
-c:v libx264 -c:a libvo_aacenc -b:v 1024k -b:a 128k -vf "scale=960:trunc(ow/a/2)*2" -tune zerolatency -preset veryfast -crf 23 -f flv rtmp://localhost:1935/hls/movie_high
-c:v libx264 -c:a libvo_aacenc -b:v 1920k -b:a 128k -vf "scale=1280:trunc(ow/a/2)*2" -tune zerolatency -preset veryfast -crf 23 -f flv rtmp://localhost:1935/hls/movie_hd720
-c copy -f flv rtmp://localhost:1935/hls/movie_src;
}
application hls {
live on;
hls on;
hls_path /tmp/hls;
hls_nested on;
hls_variant _low BANDWIDTH=288000; # Low bitrate, sub-SD resolution
hls_variant _mid BANDWIDTH=448000; # Medium bitrate, SD resolution
hls_variant _high BANDWIDTH=1152000; # High bitrate, higher-than-SD resolution
hls_variant _hd720 BANDWIDTH=2048000; # High bitrate, HD 720p resolution
hls_variant _src BANDWIDTH=4096000; # Source bitrate, source resolution
}
}
}
由于某种原因,使用缩放视频-vf "scale=..."
不起作用(使用标志也是如此-s wxh
),因为没有创建输出。我通过检查 rtmp 模块提供的统计页面来验证这一点。当我开始向服务器流式传输时,/movie 应用程序显示数据流,但 /hls 应用程序什么也没有得到。如果我删除标志,-vf "scale=..."
那么 /hls 应用程序下的 5 个流的一切都按预期工作。我做错了什么吗?我想要缩放,因为我不想在不同的比特率上发送相同的分辨率。我的 nginx 版本是 1.16.1,所有这些都在 Ubuntu 18.04 上运行。
答案1
按照@BenXO 的建议在命令行中运行 ffmpeg 命令后,我收到有关未找到 libvo_aacenc 的错误,即此代码片段是问题所在:-c:a libvo_aacenc
。快速搜索发现 ffmpeg 不再支持此编码器,建议仅使用aac
。将所有实例更改为-c:a libvo_aacenc
解决-c:a aac
了该问题。
答案2
worker_processes 1;
error_log logs/error.log;
events {
worker_connections 1024;
}
http {
keepalive_timeout 60;
send_timeout 10;
keepalive_requests 10;
client_body_timeout 10;
#gzip on;
sendfile on;
include mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log logs/access.log main;
server {
listen 80;
# listen [::]: 80 ipv6only;
server_name localhost;
access_log logs/host.access.log main;
add_header Strict-Transport-Security "max-age=63072000;";
index index.php index-nginx.html index.html index.htm index.m3u8 index.mpd;
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root site;
}
# location ~ \.php$ {
# include fastcgi_params;
# fastcgi_pass 127.0.0.1:9000;
# fastcgi_index index.php;
# fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
# }
location / {
location ~* \.m3u8$ {
add_header Cache-Control no-cache;
}
try_files $uri $uri/ =404;
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Strict-Transport-Security' 'max-age=31536000';
add_header 'X-Content-Type-Options' "nosniff" 'always';
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Max-Age' 1728000;
# add_header 'Content-Type' 'text/plain; charset=utf-8';
add_header 'Content-Length' 0;
return 204;
}
if ($request_method = 'POST') {
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Expose-Headers' 'Content-Length';
}
if ($request_method = 'GET') {
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Expose-Headers' 'Content-Length,Content-Range';
}
root site;
index index.php index.html index-nginx.html index.htm index.m3u8 index.mpd;
}
location /stat {
rtmp_stat all;
rtmp_stat_stylesheet stat.xsl;
# auth_basic "Restricted Content";
# auth_basic_user_file .htpasswd;
}
location /stat.xsl {
root site;
}
#location /control {
#rtmp_control all;
# auth_basic "stream";
# auth_basic_user_file .htpasswd;
#}
#location /publish {
# return 201;
#}
#location /play {
# return 202;
#}
#location /record_done {
# return 203;
#}
location /tmp_hls {
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Max-Age' 1728000;
add_header 'Content-Type' 'text/plain; charset=utf-8';
add_header 'Content-Length' 0;
return 204;
}
if ($request_method = 'POST') {
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Expose-Headers' 'Content-Length';
}
if ($request_method = 'GET') {
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Expose-Headers' 'Content-Length';
}
types {
application/vnd.apple.mpegurl m3u8;
text/html html;
}
autoindex on;
autoindex_localtime on;
autoindex_exact_size off;
alias X:/temp/tmp_hls; # <-----
expires -1;
}
location /tmp_dash {
alias X:/temp/tmp_dash; # <-----
autoindex on;
autoindex_localtime on;
autoindex_exact_size off;
expires -1;
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Max-Age' 1728000;
add_header 'Content-Type' 'text/plain; charset=utf-8';
add_header 'Content-Length' 0;
return 204;
}
if ($request_method = 'POST') {
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Expose-Headers' 'Content-Length';
}
if ($request_method = 'GET') {
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Expose-Headers' 'Content-Length';
}
types {
application/dash+xml mpd;
application/vnd.apple.mpegurl m3u8;
video/mp2t ts;
text/html html;
}
}
location /recordings {
alias recordings;
autoindex on;
autoindex_localtime on;
autoindex_exact_size off;
expires -1;
if ($request_method = 'OPTIONS') {
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Max-Age' 1728000;
add_header 'Content-Type' 'text/plain; charset=utf-8';
add_header 'Content-Length' 0;
return 204;
}
if ($request_method = 'POST') {
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Expose-Headers' 'Content-Length';
}
if ($request_method = 'GET') {
add_header 'Access-Control-Allow-Origin' '*' always;
add_header 'Access-Control-Allow-Methods' 'GET, POST, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'DNT,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Range';
add_header 'Access-Control-Expose-Headers' 'Content-Length';
}
types {
application/dash+xml mpd;
application/vnd.apple.mpegurl m3u8;
video/mp2t ts;
video/mp4 mp4;
text/html html;
}
}
}
}
rtmp {
server {
listen 1935;
chunk_size 4096;
application live {
live on;
interleave on;
meta on;
session_relay on;
max_connections 1500;
record_path recordings;
record_suffix all-%d-%b-%y-%T.flv;
# record_interval 30s;
# record keyframes;
push rtmp://localhost/hls;
# push rtmp://localhost/dash;
# push rtmp://localhost/youtube;
exec ffmpeg -i rtmp://localhost/$app/$name -async 1 -vsync -1
-c:v libx264 -acodec copy -b:v 256k -vf "scale=480:trunc(ow/a/2)*2" -tune zerolatency -preset veryfast -crf 23 -g 60 -hls_list_size 0 -f flv rtmp://localhost/hls/$name_low
-c:v libx264 -acodec copy -b:v 768k -vf "scale=720:trunc(ow/a/2)*2" -tune zerolatency -preset veryfast -crf 23 -g 60 -hls_list_size 0 -f flv rtmp://localhost/hls/$name_mid
-c:v libx264 -acodec copy -b:v 1024k -vf "scale=960:trunc(ow/a/2)*2" -tune zerolatency -preset veryfast -crf 23 -g 60 -hls_list_size 0 -f flv rtmp://localhost/hls/$name_high
-c:v libx264 -acodec copy -b:v 1920k -vf "scale=1280:trunc(ow/a/2)*2" -tune zerolatency -preset veryfast -crf 23 -g 60 -hls_list_size 0 -f flv rtmp://localhost/hls/$name_higher
-c copy -f flv rtmp://localhost/hls/$name_src;
}
application hls {
live on;
hls on;
hls_nested on;
hls_cleanup on;
meta copy;
# hls_sync 100ms;
hls_type live;
hls_fragment 1s;
hls_playlist_length 3s;
hls_path X:/temp/tmp_hls; # <-----
hls_fragment_naming system;
hls_variant _low BANDWIDTH=288000; # Low bitrate, sub-SD resolution
hls_variant _mid BANDWIDTH=448000; # Medium bitrate, SD resolution
hls_variant _high BANDWIDTH=1152000; # Higher-than-SD resolution
hls_variant _higher BANDWIDTH=2048000; # High bitrate, HD 720p resolution
hls_variant _src BANDWIDTH=4096000; # Source bitrate, source resolution
}
application dash {
live on;
dash on;
dash_nested on;
dash_cleanup on;
dash_fragment 1s;
dash_playlist_length 3s;
dash_path X:/temp/tmp_dash; # <-----
}
#application youtube {
#live on;
#push rtmp://a.rtmp.youtube.com/live2/YOUR_STREAM_KEY;
#allow publish 127.0.0.1;
#deny publish all;
#}
}
}