<p>
Nginx is a web server with interesting modules to extend its functionality.<br />
The Real Time Messaging Protocol (RTMP) is used to send video (&amp; audio) streams<br />
over the internet. Nginx offers a RTMP media streaming module.
</p>
<p>
Many action cams and drones support sending their video streams via RTMP.
</p>
<p>
This page is focused on the configuration of RTMP on Nginx.
</p>

<h3>Contents</h3>
<ul>
<li><a href="#install">Installation</a></li>
<li><a href="#config">RTMP configuration example</a>
<li><a href="#publish">Publishing a stream with FFmpeg</a></li>
<li><a href="#hls">HTTP Live Streaming (HLS)</a></li>
<li><a href="#links">External links</a></li>
</ul>

<h3 id="install">Installation</h3>
<pre><code class="language-bash">sudo apt install nginx libnginx-mod-rtmp
</code></pre>

<h3 id="config">RTMP configuration example</h3>
<dl class="file">
<dt><code class="filename">/etc/nginx/nginx.conf</code></dt>
<dd><pre class="file"><code class="language-nginx">#...
# For rtmp, worker_processes needs to be 1, which is the default.
#worker_processes auto;
#...

rtmp {
    server {
        listen 1935;

        # Who is allowed to connect can be handled with
        # HTTP response status codes.
        #on_connect http://example.net/rtmp_auth;

        application live {
            live on;

            hls on;
            hls_path /tmp/hls;

            dash on;
            dash_path /tmp/dash;
        }
    }
}

http {
    #...

    server {
        listen 8080;

        location /hls {
            types {
                application/vnd.apple.mpegurl m3u8;
            }
            root /tmp;
            add_header Cache-Control no-cache;
            add_header Access-Control-Allow-Origin *;
        }

        location /dash {
            types {
                application/dash+xml mpd;
            }
            root /tmp;
            add_header Cache-Control no-cache;
            add_header Access-Control-Allow-Origin *;
        }
    }
}

#...
</code></pre>
</dd>
</dl>

<p>
Reload the configuration:
</p>
<pre><code class="language-bash">sudo systemctl reload nginx
</code></pre>

<h3 id="publish">Publishing a stream with FFmpeg</h3>
<p>
The following command creates a stream named <code>stream</code> in<br />
the configured application <code>live</code>:
</p>
<pre><code class="language-bash">ffmpeg -re -i input.mp4 \
  -c:v libx264 -c:a aac \
  -f flv rtmp://example.net/live/stream
</code></pre>
<p>
Receive the stream from the RTMP server and show it on screen:
</p>
<pre><code class="language-bash">ffplay -fflags nobuffer rtmp://example.net/live/stream
</code></pre>

<h3 id="hls">HTTP Live Streaming (HLS)</h3>
<dl class="file">
<dt><code class="filename">hls.html</code></dt>
<dd><pre class="file"><code class="language-xml">&lt;!DOCTYPE html&gt;
&lt;html lang="en"&gt;
&lt;head&gt;
&lt;title&gt;HTTP Live Streaming&lt;/title&gt;
&lt;/head&gt;
&lt;body&gt;
&lt;script src="https://cdn.jsdelivr.net/npm/hls.js@1"&gt;&lt;/script&gt;
&lt;video id="video" controls&gt;&lt;/video&gt;
&lt;script&gt;
  var video = document.getElementById('video');
  var videoSrc = 'http://example.net:8080/hls/stream.m3u8';
  if (Hls.isSupported()) {
    var hls = new Hls();
    hls.loadSource(videoSrc);
    hls.on(Hls.Events.MEDIA_ATTACHED, function () {
      video.muted = true;
      video.play();
    });
    hls.attachMedia(video);
  } else if (video.canPlayType('application/vnd.apple.mpegurl')) {
    video.src = videoSrc;
  }
&lt;/script&gt;
&lt;/body&gt;
&lt;/html&gt;
</code></pre>
</dd>
</dl>
<p>
HTTP Live Streaming (HLS) adds a delay / latency of approx. 10 to 60 seconds<br />
to the live input stream.
</p>

<h3 id="links">External links</h3>
<ul>
<li><a href="https://www.nginx.com/products/nginx/modules/rtmp-media-streaming/" target="_blank">
https://www.nginx.com/products/nginx/modules/rtmp-media-streaming/</a></li>
<li><a href="https://github.com/arut/nginx-rtmp-module/wiki/Directives" target="_blank">
https://github.com/arut/nginx-rtmp-module/wiki/Directives</a></li>
<li><a href="https://trac.ffmpeg.org/wiki/StreamingGuide" target="_blank">
https://trac.ffmpeg.org/wiki/StreamingGuide</a></li>
<li><a href="https://github.com/video-dev/hls.js/#embedding-hlsjs" target="_blank">
https://github.com/video-dev/hls.js/#embedding-hlsjs</a></li>
<li><a href="https://github.com/Dash-Industry-Forum/dash.js#standard-setup" target="_blank">
https://github.com/Dash-Industry-Forum/dash.js#standard-setup</a></li>
</ul>