【问题标题】:FFMPEG pushed RTMP stream not working on Android & iPhoneFFMPEG 推送的 RTMP 流无法在 Android 和 iPhone 上运行
【发布时间】:2015-08-15 21:36:41
【问题描述】:

我必须进行半直播。我使用了 Nginx-rtmp 模块,然后通过 ffmpeg 将内容推送到它:

ffmpeg -re -i content.mp4 -r 25 -f fvl "rtmp://rtmp.server.here"

当我从“rtmp://rtmp.server.here”在 VLC 中打开流时,流运行良好

但我还必须制作播放这些流的 iPhone 和 Android 应用程序。 这就是问题所在,流在 Android 和 iPhone 上不起作用。

如果我使用 Wowza 流媒体云并流到 Wowza 云而不是我自己的 nginx-rtmp 服务器,那么为 Android 和 iPhone 编写的同一个应用程序可以很好地播放流。

现在要么 nginx-rtmp 不能正常工作,要么是什么?我也尝试过 crtmpserver 并且发生了同样的事情。

我想要达到的目标: 我必须开发一个系统,我们可以将电视频道(对其拥有权限)上传到服务器,然后制作一个网站、Android 应用程序和 iPhone 应用程序,以便消费者可以观看直播频道。

我知道上传部分,可能是电视调谐器卡和开放广播软件将其流式传输到服务器。但现场播放对我来说是新的。


更新:我也使用了 ffprobe,这是输出。 (见最后一行)

munir@munir-HP-ProBook-450-G2:~$ ffprobe rtmp://rtmp.server.here
ffprobe version 2.6.2 Copyright (c) 2007-2015 the FFmpeg developers
  built with gcc 4.8 (Ubuntu 4.8.2-19ubuntu1)
  configuration: --extra-libs=-ldl --prefix=/opt/ffmpeg --enable-avresample --disable-debug --enable-nonfree --enable-gpl --enable-version3 --enable-libopencore-amrnb --enable-libopencore-amrwb --disable-decoder=amrnb --disable-decoder=amrwb --enable-libpulse --enable-libx264 --enable-libx265 --enable-libfdk-aac --enable-libvorbis --enable-libmp3lame --enable-libopus --enable-libvpx --enable-libspeex --enable-libass --enable-avisynth --enable-libsoxr --enable-libxvid --enable-libvo-aacenc --enable-libvidstab
  libavutil      54. 20.100 / 54. 20.100
  libavcodec     56. 26.100 / 56. 26.100
  libavformat    56. 25.101 / 56. 25.101
  libavdevice    56.  4.100 / 56.  4.100
  libavfilter     5. 11.102 /  5. 11.102
  libavresample   2.  1.  0 /  2.  1.  0
  libswscale      3.  1.101 /  3.  1.101
  libswresample   1.  1.100 /  1.  1.100
  libpostproc    53.  3.100 / 53.  3.100
[flv @ 0x267cc60] Stream discovered after head already parsed
    Last message repeated 1 times
Input #0, flv, from 'rtmp://stage.funworldpk.com/live':
  Metadata:
    Server          : NGINX RTMP (github.com/arut/nginx-rtmp-module)
    displayWidth    : 320
    displayHeight   : 240
    fps             : 20
    profile         : 
    level           : 
  Duration: 00:00:00.00, start: 288.763000, bitrate: N/A
    Stream #0:0: Video: h264 (High), yuv420p, 320x240 [SAR 1:1 DAR 4:3], 20 fps, 20 tbr, 1k tbn, 40 tbc
    Stream #0:1: Data: none
    Stream #0:2: Audio: aac (LC), 22050 Hz, stereo, fltp
Unsupported codec with id 0 for input stream 1

更新 2: 我使用 Wowza 流媒体服务器的许可副本让我的流工作。现在一切正常。但显然这不是每个人的选择,这就是为什么我不将其发布为答案。

【问题讨论】:

  • 您可以尝试使用ffprobe 来检查您的流和Wowza 输出之间是否存在编码差异。
  • @aergistal 我已经用 ffprobe 输出更新了答案。
  • 比较 Wowza 和 Nginx 流的 ffprobe 输出
  • 问题解决了吗?
  • @Anatoly 我想我做到了。在这种情况下,解决方案是摆脱不稳定/错误的开源解决方案。并以每月 60 美元的价格使用 Wowza 流媒体服务器许可证:|

标签: android iphone nginx ffmpeg rtmp


【解决方案1】:
  1. 您的输入视频使用 H.264high 配置文件。

    如果您希望与 iOS 和 Android 兼容,您必须使用baseline 配置文件。 Newer iPhones 支持 mainhigh 配置文件,但 Android documentation 仅提及 baseline

    -c:v libx264 -profile baseline

  2. 不要使用原生 aac 作为音频编解码器,使用 libfdk_aac,因为它是 FFmpeg 可用的最高质量编码器,它将帮助您生成有效的 AAC 流:

    -c:a libfdk_aac

  3. 确保支持音频速率。 FLV 视频格式仅支持 11025、22050 和 44100 的采样率。

    -ar 44100

  4. ffprobe 显示不受支持的流 Stream #0:1: Data: none。使用map 跳过它:

    -map 0:0 -map 0:2

  5. (仅限 MPEG-TS)如果您使用 .ts 文件作为输入,请确保删除 AAC ADTS 标头:

    -bsf:a aac_adtstoasc

例如:

ffmpeg -re -i content.mp4 -map 0:0 -map 0:2 -c:v libx264 -vprofile baseline -preset ultrafast -tune zerolatency -r 25 -pix_fmt yuv420p -c:a libfdk_aac -ac 2 -ar 44100 -f flv rtmp://...

【讨论】:

    【解决方案2】:

    首先,我建议您添加有关该文件 (ffprobe) 的更多详细信息,以便将其与服务器输出进行比较。
    或者,在您的 ffmpeg 命令中更加严格并设置特定的输出。
    这是我用来将 RTMP 推送到 YouTube 的命令:
    ffmpeg -i any_file.mp4 -strict experimental -acodec aac -ac 1 -ar 44100 -vcodec libx264 -pix_fmt yuv420p -g 30 -vb 512k -profile:v main -preset ultrafast -r 30 -f flv -s 854x480 rtmp://a.rtmp.youtube.com/live2/your-channel.stream_code

    在您上次更新时,ffmpeg 的输出和服务器的输出之间已经存在差异:ffmpeg 创建一个 25fps 的流,而 ffprobe 看到一个 20fps 的流。
    你在服务器中设置其他输出参数的地方吗?尝试相应地设置ffmpeg 输出。

    查看更改ffmpeg 输出是否会影响服务器输出,并尝试使用 h264 主配置文件。

    关于 ffprobe 错误消息,如果您的原始文件还包含 3 个流,则服务器可能不喜欢它,因此使用 map 删除该“数据”流,如下所示:
    ffmpeg -i content.mp4 -map 0:0 -map 0:2 ...

    【讨论】:

    • 虽然较新的 iPhone 支持 mainhigh 配置文件,但 Android 文档仅提及 H.264 AVC 的 baseline 配置文件,因此如果需要,您必须使用它与两个平台的兼容性。默认的aac 编码器是推荐的(提示:-strict-experimental 部分)。有效 AAC 输出的最佳选择是 libfdk_aac
    【解决方案3】:

    RTMP 协议的使用非常有限,主要用于视频录制。没有理由使用它来播放,因为移动设备本身不支持 RTMP,您认为建议移动用户在设备上安装 VLC 或类似应用程序不是一个好主意吗?

    插件nginx-rtmp-module 已被整合到 Nginx+ 中,以在 Nginx 之外制作一个全面的录制媒体服务器,以替代 Wowza 媒体服务器或实现 HLS 以通过 HTTP 进行播放。该插件可以配合Nginx开源版使用。

    要使您的视频内容可用于移动设备,您只有 2 个选项,每个选项都通过 HTTP(s) 工作,而不是 RTMP:

    1. HTTP Live Streaming,见例子:

      location / {
          hls;
          hls_fragment            5s;
          hls_buffers             10 10m;
          hls_mp4_buffer_size     1m;
          hls_mp4_max_buffer_size 5m;
          root /var/video/;
      }
      
    2. HTTP pseudo streaming,看例子

      location /video/ {
          mp4;
          mp4_buffer_size       1m;
          mp4_max_buffer_size   5m;
          mp4_limit_rate        on;
          mp4_limit_rate_after  30s;
      }
      

      另一方面是安全性。如何保护视频流 URL?预先生成的过期 URL 是一个不错的方法,你可以试试,看我的例子there

    【讨论】:

    • 我已经更新了问题,抱歉回复晚了。之前我真的很忙于公司的其他首要任务。
    猜你喜欢
    • 1970-01-01
    • 2016-07-25
    • 1970-01-01
    • 2016-06-23
    • 2012-01-06
    • 2013-03-21
    • 1970-01-01
    • 2011-11-12
    • 2020-11-16
    相关资源
    最近更新 更多