1. 为什么选择Docker+FFmpeg搭建RTMP直播系统

去年公司内部技术分享会,我需要临时搭建一个直播系统让异地同事参与。当时试过各种商业方案,不是费用太高就是配置太复杂。最后用Docker+FFmpeg组合,30分钟就搞定了稳定运行的直播系统,成本仅为一台云服务器费用。

这种方案最大的优势就是轻量和灵活。相比动辄上万的商业直播平台,我们只需要:

  • 一台1核2G的云服务器(月费不到100元)
  • 开源的nginx-rtmp镜像(约20MB)
  • FFmpeg工具(命令行操作)

实际测试中,这套系统能稳定支持50人同时在线观看720P直播。对于企业内训、产品演示、在线教学等场景完全够用。更重要的是所有组件都在自己掌控中,不用担心第三方服务突然变更接口或收费政策。

2. 快速搭建RTMP流媒体服务器

2.1 准备Docker环境

我推荐使用Ubuntu 20.04 LTS系统,这是目前最稳定的选择。安装Docker只需两条命令:

sudo apt-get update
sudo apt-get install -y docker.io

安装完成后需要将当前用户加入docker组,避免每次都要sudo:

sudo usermod -aG docker $USER
newgrp docker  # 立即生效

验证安装是否成功:

docker --version
# 应输出类似: Docker version 20.10.12, build e91ed57

2.2 部署nginx-rtmp服务

tiangolo/nginx-rtmp是GitHub上star数最多的RTMP服务器镜像,实测非常稳定。部署只需单条命令:

docker run -d -p 1935:1935 --name rtmp-server tiangolo/nginx-rtmp

这里解释下关键参数:

  • -p 1935:1935:将容器内RTMP默认端口映射到主机
  • --name rtmp-server:给容器起个有意义的名字
  • -d:后台运行模式

如果想自定义配置,比如增加HLS支持,可以这样操作:

  1. 创建自定义配置文件nginx.conf:
rtmp {
    server {
        listen 1935;
        chunk_size 4096;
        
        application live {
            live on;
            record off;
            
            # 增加HLS支持
            hls on;
            hls_path /tmp/hls;
            hls_fragment 3s;
        }
    }
}
  1. 重新启动容器并挂载配置文件:
docker run -d -p 1935:1935 -p 8080:80 \
  -v $(pwd)/nginx.conf:/etc/nginx/nginx.conf \
  --name rtmp-server tiangolo/nginx-rtmp

3. 使用FFmpeg实现多源推流

3.1 FFmpeg安装与基础命令

在Ubuntu上安装FFmpeg:

sudo apt-get install -y ffmpeg

验证安装:

ffmpeg -version
# 应输出类似: ffmpeg version 4.2.4

最基本的推流命令(本地文件→RTMP):

ffmpeg -re -i input.mp4 -c copy -f flv rtmp://localhost/live/stream

参数解析:

  • -re:按原始帧率读取
  • -c copy:不重新编码(节省CPU)
  • -f flv:输出FLV格式(RTMP标准)

3.2 实战推流方案

场景一:屏幕直播(适合教学演示)

ffmpeg -f x11grab -s 1920x1080 -i :0.0+0,0 \
  -f pulse -i default \
  -c:v libx264 -preset ultrafast \
  -c:a aac -f flv rtmp://server_ip/live/screen

场景二:摄像头直播(适合活动直播)

ffmpeg -f v4l2 -i /dev/video0 \
  -f alsa -i hw:0 \
  -c:v libx264 -preset fast \
  -c:a aac -f flv rtmp://server_ip/live/camera

场景三:多视频轮播

ffmpeg -re -stream_loop -1 -i playlist.txt \
  -c copy -f flv rtmp://server_ip/live/playlist

其中playlist.txt内容格式:

file 'video1.mp4'
file 'video2.mp4'
file 'video3.mp4'

4. 多终端播放方案

4.1 PC端播放方案

VLC播放器:

  1. 媒体 → 打开网络串流
  2. 输入地址:rtmp://服务器IP/live/stream
  3. 点击播放

FFplay调试工具(适合开发者):

ffplay rtmp://server_ip/live/stream

4.2 移动端解决方案

Android推荐方案:

MediaItem mediaItem = MediaItem.fromUri("rtmp://server_ip/live/stream");
player.setMediaItem(mediaItem);
player.prepare();
player.play();

iOS推荐方案:

let player = AVPlayer(url: URL(string: "rtmp://server_ip/live/stream")!)
let controller = AVPlayerViewController()
controller.player = player
present(controller, animated: true) {
    player.play()
}

4.3 网页播放方案

使用hls.js播放HLS流(需nginx配置支持HLS):

<video id="video" controls></video>
<script src="https://cdn.jsdelivr.net/npm/hls.js@latest"></script>
<script>
  if(Hls.isSupported()) {
    const video = document.getElementById('video');
    const hls = new Hls();
    hls.loadSource('http://server_ip:8080/hls/stream.m3u8');
    hls.attachMedia(video);
    hls.on(Hls.Events.MANIFEST_PARSED,function() {
      video.play();
    });
  }
</script>

5. 性能优化与问题排查

5.1 服务器调优建议

Docker资源限制:

docker run -d --memory=1g --cpus=1 \
  -p 1935:1935 --name rtmp-server \
  tiangolo/nginx-rtmp

Nginx调优参数:

worker_processes auto;
events {
    worker_connections 1024;
    multi_accept on;
}

rtmp {
    server {
        listen 1935;
        buflen 300ms;
        
        application live {
            live on;
            meta copy;
            idle_streams off;
        }
    }
}

5.2 常见问题解决方案

问题一:推流延迟高

  • 解决方案:添加-preset ultrafast参数
  • 优化命令:
    ffmpeg -re -i input.mp4 -c:v libx264 -preset ultrafast \
      -tune zerolatency -g 30 -f flv rtmp://server_ip/live/stream
    

问题二:音频视频不同步

  • 解决方案:添加-async 1参数
  • 示例:
    ffmpeg -re -i input.mp4 -c:v copy -c:a aac -async 1 \
      -f flv rtmp://server_ip/live/stream
    

问题三:网络抖动导致卡顿

  • 解决方案:启用TCP协议传输
    ffmpeg -re -i input.mp4 -c copy -f flv \
      "rtmp://server_ip/live/stream live=1 protocol=tcp"
    

6. 进阶功能扩展

6.1 录制直播内容

修改nginx配置增加录制功能:

application live {
    live on;
    record all;
    record_path /var/rec;
    record_unique on;
}

然后重新挂载配置:

docker run -d -p 1935:1935 \
  -v $(pwd)/nginx.conf:/etc/nginx/nginx.conf \
  -v $(pwd)/recordings:/var/rec \
  tiangolo/nginx-rtmp

6.2 多分辨率转码

使用FFmpeg生成多种分辨率流:

ffmpeg -re -i input.mp4 \
  -c:v libx264 -preset fast -s 1280x720 -b:v 2500k -f flv rtmp://server_ip/live/720p \
  -c:v libx264 -preset fast -s 854x480 -b:v 1000k -f flv rtmp://server_ip/live/480p \
  -c:v libx264 -preset fast -s 640x360 -b:v 750k -f flv rtmp://server_ip/live/360p

6.3 安全防护措施

推流鉴权配置:

application live {
    live on;
    publish_notify on;
    on_publish http://auth_server/auth;
    on_play http://auth_server/auth;
}

IP白名单限制:

application live {
    live on;
    allow publish 192.168.1.0/24;
    deny publish all;
    allow play all;
}

在实际项目中,这套方案已经稳定运行了2年多,支撑过数百场内部培训直播。最让我惊喜的是它的灵活性——当需要新增功能时,通过修改Docker配置或调整FFmpeg参数就能快速实现。比如去年突然需要增加直播回放功能,只需在nginx配置中开启录制选项就解决了问题。

Logo

邀请您加入社区

更多推荐