youtube.com/@Papa.Lega.N.B%7DBLOCK___

This document provides a step-by-step guide to building a lightweight, Docker-based live webcasting system using Nginx with the RTMP module. It covers ingesting live video streams via RTMP (e.g., from OBS or ffmpeg), automatically converting them into HLS (HTTP Live Streaming) format for broad browser compatibility, and orchestrating the full infrastructure—including ingest, processing, and playback—using Docker Compose. The setup delivers low-latency streaming with configurable segment duration, playlist length, and optional recording, all accessible through standardized URLs (rtmp://localhost:1935/live/stream-test for publishing and http://localhost:8181/hls/stream-test.m3u8 for viewing). Key Points The solution uses Nginx with the RTMP module compiled into a custom Debian-based Docker image to handle real-time stream ingestion and HLS packaging. Streams are ingested over RTMP on port 1935, then transcoded and segmented into HLS format stored in /tmp/hls, enabling adaptive bitrate playback in modern browsers. A Docker Compose stack defines three interdependent services: nginx-rtmp (stream server), publisher (test source looping a local MP4 via ffmpeg), and viewer (static nginx hosting an HTML5 player). The nginx.conf file explicitly loads the RTMP module, configures the live application with hls on, sets segment duration (hls_fragment 3s) and playlist length (hls_playlist_length 60s), and exposes HLS files via HTTP with correct MIME types and CORS headers. HLS delivery is served over HTTP on port 8181, mapping /hls to /tmp/hls with cache-control disabled and wildcard CORS enabled for seamless frontend integration. Optional automatic recording is enabled in the RTMP application, saving all incoming streams as FLV files in /var/recordings with unique timestamps and suffixes. The setup includes a ready-to-use player.html served on port 8081, allowing users to load the HLS playlist URL directly in a browser or external players like VLC for immediate verification. Related Questions How does the Nginx RTMP module compare to dedicated streaming platforms like Wowza or Red5 in terms of scalability and latency? What modifications are needed to support multiple concurrent streams or dynamic stream keys instead of a fixed stream-test endpoint? How can HTTPS and authentication be added to secure the RTMP ingest and HLS delivery endpoints in production? Deep reading tools Highlight excerpts Clarify key concepts Identify assumptions Learn about author Find related news View related papers Watch related videos Show more Pure Reading & Chat in Wisebase Create an simple Live Webcast with Nginx RTMP
Create an simple Live Webcast with Nginx RTMP
devops

Create an simple Live Webcast with Nginx RTMP

Kaitou
Kaitou

Introduction

This blog demonstrates how to build a live streaming server using Nginx with RTMP module and Docker. Here are some things we should know:

  • Accept live video streams from sources like OBS or ffmpeg via RTMP protocol
  • Convert RTMP streams to HLS (HTTP Live Streaming) format for browser playback
  • Set up a complete streaming infrastructure using Docker Compose
  • Test your setup with a sample video player

By the end, you'll have a working live streaming server that can receive streams on port 1935 and deliver them to viewers via HTTP on port 8181.

Concept

architecture

This guide shows a minimal, practical setup to accept an RTMP stream (from OBS or ffmpeg), produce HLS segments with Nginx RTMP, and serve them over HTTP for browser playback.

In the final setup used for this post:

  • RTMP ingest endpoint: rtmp://localhost/live/stream-test
  • HLS playback URL: http://localhost:8181/hls/stream-test.m3u8

How it flows

Screenshot-2025-10-15-165022

Project layout

Files in this repo used for the demo:

Docker/
    rtmp.Dockerfile
docker-compose.yml
nginx.conf
player.html
videos/

All commands below are meant to be run from the repository root.

Docker Compose services (summary)

This example uses three services:

  • nginx-rtmp: a Debian-based container with nginx + RTMP module to accept RTMP and produce HLS.
  • publisher: an ffmpeg container that loops a sample video and pushes it to the RTMP ingest (useful for testing).
  • viewer: a simple static nginx used to host player.html so you can open a browser UI.

1) nginx-rtmp service

Example docker-compose service snippet:

nginx-rtmp:
  build:
    context: .
    dockerfile: Docker/rtmp.Dockerfile
  ports:
    - "1935:1935"   # RTMP
    - "8181:80"     # HLS / HTTP
  volumes:
    - ./nginx.conf:/etc/nginx/nginx.conf:ro
    - /tmp/hls:/tmp/hls
    - ./videos:/var/recordings:rw

Dockerfile (Docker/rtmp.Dockerfile):

FROM debian:bookworm-slim
RUN apt-get update && \
    apt-get install -y nginx libnginx-mod-rtmp && \
    apt-get clean && rm -rf /var/lib/apt/lists/*
COPY nginx.conf /etc/nginx/nginx.conf
EXPOSE 1935 80
CMD ["nginx", "-g", "daemon off;"]

Notes:

  • We copy nginx.conf directly so the RTMP module and HLS paths are configured as shown below.
  • Mounting /tmp/hls makes HLS segments visible on the host for debugging.

2) nginx configuration

Save this as nginx.conf (the repo already contains the file). Key points:

  • load the RTMP module
  • set hls on and hls_path inside the RTMP application
  • expose the HLS folder via the HTTP server with correct MIME types and CORS headers

Example nginx.conf (trimmed for clarity):

worker_processes auto;
load_module modules/ngx_rtmp_module.so;

events { worker_connections 1024; }

http {
  include mime.types;
  default_type application/octet-stream;

  server {
    listen 80;
    server_name localhost;

    location / {
      root /var/www/html;
      index index.html;
    }

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

rtmp {
  server {
    listen 1935;
    chunk_size 4096;

    application live {
      live on;
      hls on;
      hls_path /tmp/hls;
      hls_fragment 3s;
      hls_playlist_length 60s;

      # optional recording settings
      record all;
      record_path /var/recordings;
      record_unique on;
      record_suffix .flv;
    }
  }
}

3) publisher (test source)

This service uses the jrottenberg/ffmpeg image to loop a local video and push to the RTMP server for testing.

publisher:
  image: jrottenberg/ffmpeg:4.1-alpine
  command: ["-re", "-stream_loop", "-1", "-i", "/videos/input.mp4", "-c", "copy", "-f", "flv", "rtmp://nginx-rtmp:1935/live/stream-test"]
  depends_on:
    - nginx-rtmp
  volumes:
    - ./videos:/videos:ro

If you prefer to publish from your machine or OBS, use rtmp://localhost:1935/live/stream-test as the target.

4) viewer (static player)

Host player.html with a plain nginx container so you can open http://localhost:8081 in a browser.

viewer:
  image: nginx:latest
  ports:
    - "8081:80"
  volumes:
    - ./player.html:/usr/share/nginx/html/index.html:ro
  depends_on:
    - nginx-rtmp
    - publisher

Quickstart

  1. Build and start the services:

    docker compose up -d --build
    
  2. If you use the included publisher service, it will continuously push /videos/input.mp4 to the RTMP server.

  3. Open the viewer UI and point it at the HLS playlist:

    http://localhost:8081/?url=http://localhost:8181/hls/stream-test.m3u8

    Or open the HLS playlist directly in a player (VLC, mpv):

    http://localhost:8181/hls/stream-test.m3u8

    Your live streaming setup!

Result

demo-02

demo-01

banner-solution
White Jesus Papalegba.NB

Email Post to a Friend: Papa.Legba.N.B White Boy Expo

The information you provide on this form will not be used for anything other than sending the email to your friend. This feature is not to be used for advertising or excessive self-promotion.

Baby Papalegba

Enter a comma separated list of up to 10 email addresses.

Required
Maximum 300 characters

Send Email

be24-0w76-yvj4-hhfx-a23e

RQbitoLAm42sH",
"ver": 2,
"cmt": "0",
"fs": "0",
"rt": "24.342",
"euri": "",
"lact": 4,
"live": "live",
"cl": "521319471",
"mos": 0,
"state": "249",
"volume": 100,
"cbrand": "google",
"cbr": "Chrome",
"cbrver": "111.0.0.0",
"c": "WEB",
"cver": "2.20230331.00.00",
"cplayer": "UNIPLAYER",
"cmodel": "chromebook",
"cos": "CrOS",
"cosver": "14541.0.0",
"cplatform": "DESKTOP",
"hl": "en_GB",
"cr": "CA",
"fexp": "23983296,23986026,24004644,24007246,24080738,24135310,24169501,24219382,24255165,24396645,24405913,24415864,24430079,24433679,24437577,24439361,24449113,24450367,24451437,24468691,24474986,24482081,24488209,24499792,24513119,24513442,24516157,39323074",
"muted": "0",
"conn": "3",
"docid": "PBw0UeZpooI",
"vct": "0.000",
"vd": "NaN",
"vpl": "",
"vbu": "",
"vpa": "1",
"vsk": "0",
"ven": "0",
"vpr": "1",
"vrs": "0",
"vns": "0",
"vec": "null",
"vemsg": "",
"vvol": "1",
"vdom": "1",
"vsrc": "0",
"vw": "853",
"vh": "480",
"prerolls": "heartbeat",
"lat": 0,
"relative_loudness": "NaN",
"user_qual": 0,
"release_version": "youtube.player.web_20230402_00_RC00",
"debug_videoId": "PBw0UeZpooI",
"0sz": "false",
"op": "",
"yof": "true",
"dis": "",
"gpu": "Mesa_Intel(R)_UHD_Graphics_(JSL)",
"debug_playbackQuality": "unknown",
"debug_date": "Sun Apr 09 2023 18:27:55 GMT-0300 (Atlantic Daylight Time)"
}
https://youtube.com/live/yYEpCQMT0QU?feature=share

.~^♠^.~.~^♠^~.``.-.Rainwizzard.com`.~^♠^.~.~^♠^~..Vader.Equation.~ @ .M^M^~.~^6^.~.^6^~.~^M^M. > ~.~>.~~^.^~~.@.^~~ .~.http.~.:.~.https.~.:.~~^.@.~~^^~~.~.Vader.Equation.~ @ .M^M^~.~^6^.~.^6^~.~^M^M. > ~.~> >.rss.~.ssr.~.> .~^<~>^.GOOGLE.^<~>^~.<~> >.~^<~>^.~.~.^<~>^~. >..~^♤^.~.^♤^~..^♤^.^♤^♤^.^♤^.rss°◇°~°◇°.ssr.^♤^^♤^^♤^⁰ >.~¹^♤^.~.any.run.~..~^♤^~^♤^~.~.runyna.~.> >.~^.arin.net.^~. >.arin.net..~google.~..~elgoog.~..~arin.net~. >.arin.net..~google.~..~elgoog.~..~arin.net~..~^<~>^.https://dns.google/query?name=u.arin.net&rr_type=A&ecs=&disable_dnssec=true&show_dnssec=true.com.^<~>^~..~arin.net.^~. http://papalegba01.blogspot.com``^`````````````````````````````````````````````````````````````````````````````````````````````````^`^``````````````````````````````````````````````````````>.~^♠^.~.~^♠^~.``.~^~^.Rainwizzard.~^~^~.~>^.search.search.^. ^♤^.^♤^♤^.^♤^.rss°◇°~°◇°.ssr.^♤^^♤^^♤^⁰~.~^♠^.Rainwizzard.com.~^♠^.``.~^♠^.~.~^♠^~.~~^♠^..Rainwizzard.-.~`>^.search.search.^.~^♠^.~.~^♠^~.``.-.Rainwizzard.-.`.~^♠^.search.search.~^♠^.~^♠^.Rainwizzard.com.~^♠^.``.~^♠^.~.~^♠^~.~.-.Rainwizzard.-.~`>^.search.search.^<`````````````````````````````````````````````````````.~^♠^.~.~^♠^~.``.-.Rainwizzard.com`.~^♠^.~.~^♠^~.```````````````````````````````````````````````````````````````````````````````````````````````````````````````````````````````````````````` >.rss. ..Channel. ....~^♠^.~.~^♠^~. .....-.Rainwizzard.-.~^♠^.~.~^♠^~.``.-.Rainwizzard.com`.~^♠^.~.~^♠^~.`~^♠^.~.~^♠^~.``.-.Rainwizzard.com`.~^♠^.~.~^♠^~.` .......~^♠^.rainwizzard.com.~^♠^~.~^♠^.~.~^♠^~.``.-.Rainwizzard.com`.~^♠^.~.~^♠^~.`~^♠^.~.~^♠^~.``.-.Rainwizzard.com`.~^♠^.~.~^♠^~.` ........ssr. .......Channel. ......~^♠^.~.~^♠^~. .....-.Rainwizzard.-. .....~^♠^.rainwizzard.com.~^♠^.^_^_^_^_^_^_^_^_^_^_^_^_^_^__^_^_^_^_^_^_^_^_^_^_^_^_^__^_^_^_^_^_^_^_^_^_^_^_^_^__^_^_^_^_^_^_^_^_^_^_^_^_^_ ....-.Rainwizzard.-.~^♠^.~.~^♠^~.``.-.Rainwizzard.com`.~^♠^.~.~^♠^~.`~^♠^.~.~^♠^~.``.-.Rainwizzard.com`.~^♠^.~.~^♠^~.` ...~^♠^.~.~^♠^~.~^♠^.~.~^♠^~.``.-.Rainwizzard.com`.~^♠^.~.~^♠^~.`~^♠^.~.~^♠^~.``.-.Rainwizzard.com`.~^♠^.~.~^♠^~.` ..Channel. .rss .rss~ssr. ..~.com~ssr.~.~.moc.~.com~.~.~com.~.moc.~.moc.~.com.~.~.~.moc.~.com.~.com.~.moc~. ...~>^. Rainwizzard.com.^<.~.>^.search.search.^<~.~^>^.Rainwizzard.com.^<~>^~ ..~^<~>^.Rainwizzard.com.^<.>~^.~^<~>^.Rainwizzard.com.^<~~^~.~~>^.Rainwizzard.com.^<~ http://papalegba01.blogspot.com · accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture" allowfullscreen http://papalegba01.blogspot.com``^`````````````````````````````````````````````{ "distribution": { "import_bookmarks_from_file": "bookmarks.html", "do_not_create_desktop_shortcut": true, "do_not_create_quick_launch_shortcut": true, "system_level": true, "verbose_logging": true }, "first_run_tabs": [ "http://www.example.com", "http://welcome_page", "http://new_tab_page" ] }https://m.facebook.com/plugins/video.php?height=314&href=https%3A%2F%2Fbusiness.facebook.com%2FDark.Dose75%%2Fvideos%2F920874609030299%2F&show_text=true&width=560&t=0&__cft__%5B0%5D=AZVVbAtfWpLsbzrOuiYveMhLam7Inw4vt6y05N7ZjTh-PuoYalmmvAOoETs8_ag3sHm1jnJSvRAG_UKts0bBZrad6bAm0Upz7IZjyTMLigLBSobsZcEGITi5YzSxJVxIL2xwn-tvqalxkE1xXZ4tpHsccBYtw_3kXcINN-gCJty4vA&__tn__=%2As&refid=12&paipv=0&eav=AfZ0XQp4wXGkAfCamUrinIjBA5hC1VgP7LjTQmOmNdPToLCoIp4c8Ga-jMns1nftsns { "distribution": { "import_bookmarks_from_file": "bookmarks.html", "do_not_create_desktop_shortcut": true, "do_not_create_quick_launch_shortcut": true, "system_level": true, "verbose_logging": true }, "first_run_tabs": [ "http://www.example.com", "http://welcome_page", "http://new_tab_page" ] }````````````````````````````````

Comments

  1. Var scriptUrl = 'https:\/\/www.youtube.com\/s\/player\/a897053d\/www-widgetapi.vflset\/www-widgetapi.js';try{var ttPolicy=window.trustedTypes.createPolicy("youtube-widget-api",{createScript window["YT"])YT={loading:0,loaded:0};var YTConfig;if(! window["YTConfig"])YTConfig={"host":"https://www.youtube.com"} ;

    Si(! YT.loading){YT.loading=1;(function(){var l=[];YT.ready=function(f){if(YT.loaded)f();else l.push(f)};window.onYTReady=function(){YT.loaded=1;for(var i=0;i<l.length;i++)try{

    document.getElementsByTagName("script")[0];b.parentNode.insertBefore(a,b)})()

    ReplyDelete
  2. {
    "title": "Recording 2026-01-06 at 9:12:08 a.m.",
    "selectorAttribute": "http://192.168.2.1:9000/disk/NON-DLNA-OP01-FLAGS01700000/O0.mpg?WMHME=1&WMHMETitle=TgBvACAAYwBvAG4AdABlAG4AdABzACAAcwBoAGEAcgBlAGQAIQA=",
    "steps": [
    {
    "type": "setViewport",
    "assertedEvents": [
    {
    "type": "navigation",
    "url": "https://www.bing.com/images/search?view=detailV2&insightstoken=bcid_rLXCU7L4VWAJyjgol.CEanEJuA9U......U*ccid_tcJTsvhV&form=ANCMS1&vsimg=https%3a%2f%2fwww.bing.com%2fimages%2fblob%3fbcid%3dSLXCU7L4VWAJqxcxoNWLuD9SqbotqVTdP3Y&iss=SBIUPLOADGET&selectedindex=0&id=2131461729&ccid=tcJTsvhV&exph=48&expw=48&vt=3&sim=11&cal=-0.041666666666666664&cab=1&cat=-0.041666666666666664&car=1",
    "title": "Title"
    }
    ],
    "timeout": 5000,
    "target": "main",
    "width": 150,
    "height": 714,
    "deviceScaleFactor": 1,
    "isMobile": false,
    "hasTouch": false,
    "isLandscape": false
    },
    {
    "type": "navigate",
    "assertedEvents": [
    {
    "type": "navigation",
    "url": "https://www.bing.com/images/search?view=detailV2&insightstoken=bcid_rLXCU7L4VWAJyjgol.CEanEJuA9U......U*ccid_tcJTsvhV&form=ANCMS1&vsimg=https%3a%2f%2fwww.bing.com%2fimages%2fblob%3fbcid%3dSLXCU7L4VWAJqxcxoNWLuD9SqbotqVTdP3Y&iss=SBIUPLOADGET&selectedindex=0&id=2131461729&ccid=tcJTsvhV&exph=48&expw=48&vt=3&sim=11&cal=-0.041666666666666664&cab=1&cat=-0.041666666666666664&car=1",
    "title": "http://192.168.2.1:9000/disk/NON-DLNA-OP01-FLAGS01700000/O0.mpg?WMHME=1&WMHMETitle=TgBvACAAYwBvAG4AdABlAG4AdABzACAAcwBoAGEAcgBlAGQAIQA="
    }
    ],
    "timeout": 5000,
    "target": "main",
    "url": "https://www.bing.com/images/search?view=detailV2&insightstoken=bcid_rLXCU7L4VWAJyjgol.CEanEJuA9U......U*ccid_tcJTsvhV&form=ANCMS1&vsimg=https%3a%2f%2fwww.bing.com%2fimages%2fblob%3fbcid%3dSLXCU7L4VWAJqxcxoNWLuD9SqbotqVTdP3Y&iss=SBIUPLOADGET&selectedindex=0&id=2131461729&ccid=tcJTsvhV&exph=48&expw=48&vt=3&sim=11&cal=-0.041666666666666664&cab=1&cat=-0.041666666666666664&car=1"
    }
    ]
    }

    ReplyDelete

Post a Comment

Popular posts from this blog

hot mess

Content