- Download and install Ubuntu, (e.g. server 22.04)
- Configure server with static IP address
- Install Nginx-RTMP
sudo apt update
sudo apt install libnginx-mod-rtmpffmpeg can be used for streaming a pre-recorded video directly from this server. It is useful for testing.
sudo apt install ffmpegyoutube-dl can be used for downloading streaming content from YouTube or elsewhere.
sudo apt install youtube-dlyoutube-dl can simply be run using a command like:
youtube-dl https://www.youtube.com/watch?v=iom_nhYQIYkThis will only work once the RTMP service is running. The command to use later is:
ffmpeg -re -i "Introducing App Platform by DigitalOcean-iom_nhYQIYk.mp4" -c:v copy -c:a aac -ar 44100 -ac 1 -f flv rtmp://localhost/live/streamStreaming at multiple different qualities (Transcoding) can be done as follows, but RTMP must first be configured using dash_variant and/or hls_variant
ffmpeg -re -i "Test Video.mp4" \
-c:a aac -ac 2 -b:a 128k -c:v libx264 -pix_fmt yuv420p -profile:v baseline -preset ultrafast -tune zerolatency -vsync cfr -x264-params "nal-hrd=cbr" -b:v 500k -minrate 500k -maxrate 500k -bufsize 1000k -g 60 -s 640x360 -f flv rtmp://example.com/dash/streamname_low \
-c:a aac -ac 2 -b:a 128k -c:v libx264 -pix_fmt yuv420p -profile:v baseline -preset ultrafast -tune zerolatency -vsync cfr -x264-params "nal-hrd=cbr" -b:v 1500k -minrate 1500k -maxrate 1500k -bufsize 3000k -g 60 -s 1280x720 -f flv rtmp://example.com/dash/streamname_med \
-c:a aac -ac 2 -b:a 128k -c:v libx264 -pix_fmt yuv420p -profile:v baseline -preset ultrafast -tune zerolatency -vsync cfr -x264-params "nal-hrd=cbr" -b:v 5000k -minrate 5000k -maxrate 5000k -bufsize 10000k -g 60 -s 1920x1080 -f flv rtmp://example.com/dash/streamname_high Edit the nginx.conf file using nano which may need installing first.
sudo apt install nano /Y
sudo nano /etc/nginx/nginx.confAdd the following text to the end:
rtmp {
server {
listen 1935;
chunk_size 4096;
allow publish 127.0.0.1;
deny publish all;
# Specify buffer settings
buflen 5s; # Set the buffer length
application live {
live on;
record off;
}
}
}
Note allow publish ip-address; # is the IP address that streams may be receive from. This will need modifying to accept a stream from another server e.g. OBS or ProPresenter7.
When the application is called live then the target can be set as follows:
rtmp://ip-address/live
The path or the key can be whatever you want e.g.: obs_stream
Warning Ensure the RMTP server settings in nginx.conf is configured to allow publish from the sending ip-address.
To watch the RTMP stream from the local server:
- Use VLC player
- Open Network Stream
rtmp://ip-address/live/obs_stream
The monitoring site will be available at port 8080
Creating the following configuration:
sudo nano /etc/nginx/site-available/rtmpAdd the following contents:
server {
listen 8080;
server_name localhost;
# rtmp stat
location /stat {
rtmp_stat all;
rtmp_stat_stylesheet stat.xsl;
}
location /stat.xsl {
root /var/www/html/rtmp;
}
# rtmp control
location /control {
rtmp_control all;
}
}Create the necessary folders and templates:
sudo mkdir /var/www/html/rtmp
sudo gunzip -c /usr/share/doc/libnginx-mod-rtmp/examples/stat.xsl.gz > /var/www/html/rtmp/stat.xsl
sudo ln -s /etc/nginx/sites-available/rtmp /etc/nginx/sites-enabled/rtmpView your stats at http://ip-address:8080/stat
To add HLS and MPEG DASH support we need the following configuration without our live application:
sudo nano /etc/nginx/nginx.confCreate the config to match:
...
rtmp {
server {
...
application live {
live on;
record off;
hls on;
hls_path /var/www/html/stream/hls;
hls_fragment 3;
hls_playlist_length 60;
dash on;
dash_path /var/www/html/stream/dash;
}
}
}
...Now create the necessary directory and edit the rtmp site config
sudo mkdir /var/www/html/stream
sudo nano /etc/nginx/sites-available/rtmp. . .
server {
listen 8088;
location / {
add_header Access-Control-Allow-Origin *;
root /var/www/html/stream;
}
}
types {
application/dash+xml mpd;
}Note Now reload the configuration.
HLS: http://ip-address:8088/hls/stream.m3u8
DASH: http://ip-address:8088/dash/stream.mpd
You need a player such as a Chrome extension. However there is a player here: https://reference.dashif.org/dash.js/latest/samples/dash-if-reference-player/index.html
Enter the URL as above to view the stream.
rtmp {
server {
listen 1935;
chunk_size 4096;
publish_time_fix off;
application dash {
live on;
record off;
allow publish ip-address;
allow publish 127.0.0.1;
deny publish all;
# Copy incoming streams to the HLS application
exec ffmpeg -re -i rtmp://localhost:1935/$app/$name -c:v copy -c:a copy -f flv rtmp://localhost:1935/hls/${name};
dash on;
dash_nested on;
dash_path /tmp/dash;
dash_fragment 3;
dash_playlist_length 120;
dash_cleanup on;
dash_clock_compensation http_head;
dash_clock_helper_uri https://<your_server_domain_here>/time;
dash_variant _low bandwidth="500000" width="640" height="360";
dash_variant _med bandwidth="1500000" width="1280" height="720";
dash_variant _high bandwidth="5000000" width="1920" height="1080" max;
}
application hls {
live on;
hls on;
hls_path /tmp/hls;
hls_nested on;
hls_variant _low BANDWIDTH=500000;
hls_variant _med BANDWIDTH=1500000;
hls_variant _high BANDWIDTH=5000000;
}
}
}sudo systemctl reload nginxIn order to push the stream out to other servers such as YouTube or Facebook the following can be used:
sudo nano /etc/nginx/nginx.conf application relays {
live on;
push rtmp1.youtube.com;
push rtmp1.facebook.com;
}Note Don't forget to reload the configuration.
If you have a firewall such as ufw then the following rules will be required:
- 8088/tcp #dash or hls streams
- 1935/tcp #rtmp streams
- 8080/tcp #stats page
In ufw use the following:
sudo ufw allow from your_ip_address to any port http-alt
sudo ufw allow 8088/tcp
sudo ufw allow 1935/tcpIf the server can have a subdomain e.g. live.example.com then the certificate will apply to that. Then we may use some dynamic dns service to keep the dns entry updated if we don't have a static IP.
- Install letsencrypt
sudo apt install letsencrypt - Stop nginx
sudo systemctl stop nginx - sudo letsencrypt certonly
- Edit /etc/nginx/nginx.conf
server {
listen 80;
server_name <your_server_domain_here>;
return 301 https://$host$request_uri;
}
server {
listen 443 ssl;
server_name <your_server_domain_here>;
ssl_certificate /etc/letsencrypt/live/<your_server_domain_here>/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/<your_server_domain_here>/privkey.pem;
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
ssl_prefer_server_ciphers on;
ssl_dhparam /etc/ssl/certs/dhparam.pem;
ssl_ciphers 'ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-GCM-SHA384:DHE-RSA-AES128-GCM-SHA256:DHE-DSS-AES128-GCM-SHA256:kEDH+AESGCM:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:DHE-RSA-AES128-SHA256:DHE-RSA-AES128-SHA:DHE-DSS-AES128-SHA256:DHE-RSA-AES256-SHA256:DHE-DSS-AES256-SHA:DHE-RSA-AES256-SHA:AES128-GCM-SHA256:AES256-GCM-SHA384:AES128-SHA256:AES256-SHA256:AES128-SHA:AES256-SHA:AES:CAMELLIA:DES-CBC3-SHA:!aNULL:!eNULL:!EXPORT:!DES:!RC4:!MD5:!PSK:!aECDH:!EDH-DSS-DES-CBC3-SHA:!EDH-RSA-DES-CBC3-SHA:!KRB5-DES-CBC3-SHA';
ssl_session_timeout 1d;
ssl_session_cache shared:SSL:50m;
ssl_stapling on;
ssl_stapling_verify on;
add_header Strict-Transport-Security max-age=15768000;
...