Media Architecture, RTP topologies


With the sudden onset of Covid-19 and building trend of working-from-home , the demand for building scalable conferncing solution and virtual meeting room has skyrocketed . Here is my advice if you are building a auto- scalable conferencing solution

This article is about media server setup to provide mid to high scale conferencing solution over SIP to various endpoints including SIP softphones , PBXs , Carrier/PSTN and WebRTC.

Point to Point

Endpoints communicating over unicast. RTP and RTCP tarffic is private between sender and reciver even if the endpoints contains multiple SSRC’s in RTP session.

Advantages of P2p Disadvantages of p2p
(+) Facilitates private communication between the parties (-) Only limitaion to number of stream between the partcipants are the physical limiations such as bandwidth, num of available ports

Point to Point via Middlebox

Same as above but with a middle-box involved. Middle Box type are :

Translator

Mostly used interoperability for non-interoperable endpoints such as transcoding the codecs or transport convertion. This does not use an SSRC of its own and keeps the SSRC for an RTP stream across the translation.

Subtypes of Multibox :

Transport/Relay Anchoring

Roles like NAT traversal by pinning the media path to a public address domain relay or TURN server

Middleboxes for auditing or privacy control of participant’s IP

Other SBC ( Session Border Gateways) like characteristics are also part of this topology setup

Transport translator

interconnecting networks like multicast to unicast

media packetization to allow other media to connect to the session like non-RTP protocols

Media translator

Modifies the media inside of RTP streams commonly known as transcoding.

It can do up to full encoding/decoding of RTP streams. In many cases it can also act on behalf of non-RTP supported endpoints, receiving and responding to feedback reports ad performing FEC ( forward error corrected )

Back-To-Back RTP Session

Mostly like middlebox like translator but establishes separate legs RTP session with the endpoints, bridging the two sessions.

Takes complete responsibility of forwarding the correct RTP payload and maintain the relation between the SSRC and CNAMEs

Advantages of Back-To-Back RTP SessionDisadvantages of Back-To-Back RTP Session
(+) B2BUA / media bridge take responsibility tpo relay and manages congestion(-) It can be subjected to MIM attack or have a backdoor to eavesdrop on conversations

Point to Point using Multicast

Any-Source Multicast (ASM)

traffic from any particpant sent to the multicat group address reaches all other partcipants

Source-Specific Multicast (SSM)

Selective Sender stream to the multicast group which streams it to the recibers

Point to Multipoint using Mesh

many unicast RTP streams making a mesh

Point to Multipoint + Translator

Some more variants of this topology are Point to Multipoint with Mixer

Media Mixing Mixer

receives RTP streams from several endpoints and selects the stream(s) to be included in a media-domain mix. The selection can be through

static configuration or by dynamic, content-dependent means such as voice activation. The mixer then creates a single outgoing RTP stream from this mix.

Media Switching Mixer

RTP mixer based on media switching avoids the media decoding and encoding operations in the mixer, as it conceptually forwards the encoded media stream.

The Mixer can reduce bitrate or switch between sources like active speakers.

SFU ( Selective Forwarding Unit)

Middlebox can select which of the potential sources ( SSRC) transmitting media will be sent to each of the endpoints. This transmission is set up as an independent RTP Session.

Extensively used in videoconferencing topologies with scalable video coding as well as simulcasting.

Advantges of SFUDisadvatages of SFU
(+) Low lanetncy and low jitter buffer requirnment by avoiding re enconding
(+) saves on encoding decoding CPU utilization at server
(-) unable to manage network and control bitrate
(-) creates higher load on receiver when compared with MCU

On a high level, one can safely assume that given the current average internet bandwidth, for count of peers between 3-6 mesh architectures make sense however any number above it requires centralized media architecture.

Among the centralized media architectures, SFU makes sense for atmost 6-15 people in a conference however is the number of participants exceed that it may need to switch to MCU mode.

Simulcast

Encode in multiple variation and let SFU decide which endpoint should receive which stream type

Advantages of SFU +SimulcastDisadvantages of SFU +Simulcast
(+) Simulcast can ensure endpoints receive media stream depending on their requirnment/bandwidth/diaply(-) Uplink bandwidth reuirnment is high
(-) CPU intensive for sender for encoding many variations of outgoing stream

SVC ( scalable Video Coding)

Encodes in multiple layers based on various modalities such as

  • Signal to noise ration
  • temporal
  • Spatial
Advantages of SFU +SimulcastDisadvantages of SFU +Simulcast
(+) Simulcast can ensure endpoints receive media stream depending on their requirnment/bandwidth/diaply(-) Uplink bandwidth reuirnment is high
(-) CPU intensive for sender for encoding many variations of outgoing stream

Hybrid Topologies

There are various topologies for multi-endpoint conferences. Hybrid topologies include forward video while mixing audio or auto-switching between the configuration as load increases or decreases or by a paid premium of free plan

Hybrid model of forwarding and mixed streamings

Some endpoints receive forwarded streams while others receive mixed/composited streams.

Serverless models

Centralized topology in which one endpoint serves as an MCU or SFU.

Used by Jitsi and Skype

Point to Multipoint Using Video-Switching MCUs

Much like MCU but unlike MCU can switch the bitrate and resolution stream based on the active speaker, host or presenter, floor control like characteristics.

This setup can embed the characteristics of translator, selector and can even do congestion control based on RTCP

To handle a multipoint conference scenario it acts as a translator forwarding the selected RTP stream under its own SSRC, with the appropriate CSRC values and modifies the RTCP RRs it forwards between the domains

Cascaded SFUs

SFU chained reduces latency while also enabling scalability however takes a toll on server network as well as endpoint resources

Transport Protocols

Before getting into an in-depth discussion of all possible types of Media Architectures in VoIP systems, let us learn about TCP vs UDP.

TCP is a reliable connection-oriented protocol that sends REQ and receives ACK to establish a connection between communicating parties. It sequentially ends packets which can be resent individually when the receiver recognizes out of order packets. It is thus used for session creation due to its errors correction and congestion control features.

Once a session is established it automatically shifts to RTP over UDP. UDP even though not as reliable, not guarantying non-duplication and delivery error correction is used due to its tunnelling methods where packets of other protocols are encapsulated inside of UDP packet. However to provide E2E security other methods for Auth and encryption are used.

Audio PCAP storage and Privacy constraints for Media Servers

A Call session produces various traces for offtime monitoring and analysis which can include

CDR ( Call Detail Records ) – to , from numbers , ring time , answer time , duration etc

Signalling PCAPS – collected usually from SIP application server containing the SIP requests, SDP and responses. It shows the call flow sequences for example, who sent the INVITE and who send the BYE or CANCEL. How many times the call was updated or paused/resumed etc .

Media Stats – jitter , buffer , RTT , MOS for all legs and avg values

Audio PCAPS – this is the recording of the RTP stream and RTCP packets between the parties and requires explicit consent from the customer or user . The VoIP companies complying with GDPR cannot record Audio stream for calls and preserve for any purpose like audit , call quality debugging or an inspection by themselves.

Throwing more light on Audio PCAPS storage, assuming the user provides explicit permission to do so , here is the approach for carrying out the recording and storage operations.

Firther more , strict accesscontrol , encryption and annonymisation of the media packets is necessary to obfuscate details of the call session.

References :

To learn about the difference between Media Server tologies

  • centralized vs decentralised,
  • SFU vs MCU ,
  • multicast vs unicast ,

Read – SIP conferecning and Media Bridge

SIP conferencing and Media Bridges

SIP is the most popular signalling protocol in VOIP ecosystem. It is most suited to a caller-callee scenario , yet however supporting scalable conferences on VOIP is a market demand. It is desired that SIP must for multimedia stream but also provide conference control for building communication and collaboration apps for new and customisable solutions.

To read more about buildinga scalable VoIP Server Side architecture and

  • Clustering the Servers with common cache for High availiability and prompt failure recovery
  • Multitier archietcture ie seprartion between Data/session and Application Server /Engine layer
  • Micro service based architecture ie diff between proxies like Load balancer, SBC, Backend services , OSS/BSS etc
  • Containerization and Autoscalling

Read – VoIP/ OTT / Telecom Solution startup’s strategy for Building a scalable flexible SIP platform

VoIP/ OTT / Telecom Solution startup’s strategy for building a scalable flexible SIP platform

Scalable and Flexible platform. Let’s go in-depth to discuss how can one go about achieving scalability in SIP platforms. ulti geography Scaled via Universal Router, Cluster SIP telephony Server for High Availability, Multi-tier cluster architecture, Role Abstraction / Micro-Service based architecture, uted Event management and Event Driven architecture , Containerization, autoscaling , security , policies and market differentiator, ticketing and issue tracking.

JANUS as WebRTC SFU

Thsi article is to introduce to Janus based SFU media architecture for WebRTC systems . It also aims at evaluating the perfiormace of VP9 simulcast p2p model with Janus based SFU system. We know Jnaus is a popular WebRTC Sever with support for all WebRTC compoenents like JSEP/SDP , ICE, DTLS-SRTP, DataChannels. Its plugins expose Janus API over different transports – HTTP, WS, rabbitMQ, Unix sockets, MQTT so on. Other plugins provide deeper modificatiosn such as Video SFU, Audio MCU, SIP/RTSP gateways, broadcasting etc.

Centralised media conferencing / mixing service using Janus

Streaming Video via CDN

Tip : use mixing for Audio and Relay for video in large participant sessions.

Server Selection and Setup from source

Janus Setup on public ec2 isntance. Since the a media server can clog the server space make sure to choose alarge instance like c5.large. Sample log file size

Install prerequisite libraries

sudo apt-get install libmicrohttpd-dev libjansson-dev libnice-dev libssl-dev libsrtp-dev libsofia-sip-ua-dev libglib2.0-dev libopus-dev libogg-dev libini-config-dev libcollection-dev libwebsockets-dev pkg-config gengetopt automake libtool doxygen graphviz git libconfig-dev cmake

Make Sure libsrtp v2.x is installed instead of existing 1.4 in debain /ubuntu default such as

libsrtp0-dev is already the newest version (1.4.5~20130609~dfsg-2ubuntu1).

Manually installing libsrtp2 from https://github.com/cisco/libsrtp

wget https://github.com/cisco/libsrtp/archive/v2.2.0.tar.gz
tar xfv v2.2.0.tar.gz
cd libsrtp-2.2.0
./configure --prefix=/usr --enable-openssl
make shared_library && sudo make install

Since we are going to use websocket as signalling, ensure lws (libwebsocket) >= 2.0.0 is installed

git clone https://libwebsockets.org/repo/libwebsockets
cd libwebsockets
mkdir build
cd build
cmake -DLWS_MAX_SMP=1 -DLWS_WITHOUT_EXTENSIONS=0 -DCMAKE_INSTALL_PREFIX:PATH=/usr -DCMAKE_C_FLAGS="-fpic" 
make && sudo make install

Also libnice (at least v0.1.16) need to be installed

Get Janus source code and configure

git clone git://github.com/meetecho/janus-gateway.git
cd janus-gateway
sh autogen.sh
./configure 
--disable-data-channels 
--disable-docs 
--prefix=/opt/janus LDFLAGS="-L/usr/local/lib -Wl,-rpath=/usr/local/lib" CFLAGS="-I/usr/local/include"

At this point Janus prinst a config detail such as below and asks if its ok . Ensure Websocket is yes. One can start the make process if it is

Compiler:                  gcc
libsrtp version:           2.x
SSL/crypto library:        OpenSSL
DTLS set-timeout:          not available
Mutex implementation:      GMutex (native futex on Linux)
DataChannels support:      no
Recordings post-processor: no
TURN REST API client:      no
Doxygen documentation:     no
Transports:
    REST (HTTP/HTTPS):     yes
    WebSockets:            yes
    RabbitMQ:              no
    MQTT:                  no
    Unix Sockets:          yes
    Nanomsg:               no
Plugins:
    Echo Test:             yes
    Streaming:             yes
    Video Call:            yes
    SIP Gateway:           yes
    NoSIP (RTP Bridge):    yes
    Audio Bridge:          yes
    Video Room:            yes
    Voice Mail:            yes
    Record&Play:           yes
    Text Room:             yes
    Lua Interpreter:       no
    Duktape Interpreter:   no
Event handlers:
    Sample event handler:  no
    WebSocket ev. handler: yes
    RabbitMQ event handler:no
    MQTT event handler:    no
    Nanomsg event handler: no
    GELF event handler:    yes
External loggers:
    JSON file logger:      no
JavaScript modules:        no

Make and install

make && sudo make install

Making configs

sudo make configs

For details refer to actual README on Janus git repo https://github.com/meetecho/janus-gateway

Start

By default, Janus starts in foreground, as a console application that stop with Ctrl + c command

./janus

Starting janus as backvroudn or daemon service

sudo ./janus -N -d 0 --daemon --log-file /var/log/janus

tailing the log file

> tail -f /var/log/janus
---------------------------------------------------
  Starting Meetecho Janus (WebRTC Server) v0.11.1
---------------------------------------------------

Checking command line arguments...
Debug/log level is 0
Debug/log timestamps are disabled
Debug/log colors are enabled

references : https://janus.conf.meetecho.com/docs/service.html

Issues with installation of janus

Before resolving any issue, it is important to verify whether you are runing multiple versions of janus on your system

altanai@xx:~/janus-gateway$ janus --version
Janus commit: bed081c03ad4854f3956898646198100a8ed82cf
Compiled on:  Fri Apr  2 07:28:14 UTC 2021

janus 0.11.1

altanai@xx:~/janus-gateway$ ./janus --version
Janus commit: c970528037d46d52a4bc1fd7db2a44c900c2baf2
Compiled on:  Thu Apr  8 18:01:36 UTC 2021

janus 0.10.8

If this si so delete the one you dont require . I d go with rmeoove the one installed globally .

Cmake version error

If you see an error in rabbitmq instalation , which is part of janus installation

CMake 3.12...3.18 or higher is required.  You are running version 3.10.2

then proceed to remove existing version and install updates ne by first removing tghe existing cmake version

sudo apt remove cmake
wget https://github.com/Kitware/CMake/releases/download/v3.20.1/cmake-3.20.1-linux-x86_64.sh
sh cmake-3.20.1-linux-x86_64.sh

check version

>> cmake-3.20.1-linux-x86_64/bin/cmake --version
cmake version 3.20.1

lib websocket error in libjanus_websockets.so

Couldn't load transport plugin 'libjanus_websockets.so': /opt/janus/lib/janus/transports/libjanus_websockets.so: undefined symbol: lws_hdr_custom_length

Libwebsockets (LWS) is a flexible, lightweight pure C library for implementing modern network protocols easily with a tiny footprint, using a nonblocking event loop.

Fisrt check the version of libwebsockets u have on ur machine . If it is lesse that 2.0.0 version

>> apt show libwebsockets-dev

Package: libwebsockets-dev
Version: 2.0.3-3build1
Priority: optional
Section: universe/libdevel
Source: libwebsockets
Origin: Ubuntu
Maintainer: Ubuntu Developers <ubuntu-devel-discuss@lists.ubuntu.com>
Original-Maintainer: Laszlo Boszormenyi (GCS) <gcs@debian.org>
Bugs: https://bugs.launchpad.net/ubuntu/+filebug
Installed-Size: 502 kB
Depends: libwebsockets8 (= 2.0.3-3build1), libev-dev, libssl-dev, libuv1-dev, zlib1g-dev
Homepage: https://libwebsockets.org/
Download-Size: 133 kB
APT-Manual-Installed: yes
APT-Sources: http://us-west-1.ec2.archive.ubuntu.com/ubuntu bionic/universe amd64 Packages
Description: lightweight C websockets library - development files
 Libwebsockets is a lightweight pure C library for both websockets
 clients and servers built to use minimal CPU and memory resources
 and provide fast throughput in both directions.
 .
 This package contains the header files needed for developing programs
 using libwebsockets and a static library.

Follow the steps to install libwebsocket ,  libwebsockets >= 2.0.0, the current v3.2-stable is good http://libwebsockets.org/

Failures due to ICE

ICE failed for component 1 in stream 1… 
No WebRTC media anymore
 WebRTC resources freed;

Self Signed SSL certs

Make a new directory for SSL certs

mkdir /home/ubuntu/ssl

generate certs 

openssl req -new -newkey rsa:4096 -nodes -keyout key.pem -out cert.csr
openssl x509 -req -sha256 -days 365 -in cert.csr -signkey key.pem -out cert.pem
chmod 600 cert.csr
chmod 600 cert.pem
chmod 600 key.pem

Remember to allow advanced access if the ssl are self signed and not from a varified CA

Update janus config

Path for Janus configuration is usually /opt/janus/etc/janus/janus.jcfg as given by the prefix during instalation. some of the types of config are

>> vi /opt/janus/etc/janus/janus.jcfg
general: {
   configs_folder = "/opt/janus/etc/janus" # Configuration files folder
   plugins_folder = "/opt/janus/lib/janus/plugins" # Plugins folder
   transports_folder = "/opt/janus/lib/janus/transports" # Transports folder
   events_folder = "/opt/janus/lib/janus/events" # Event handlers folder
   loggers_folder = "/opt/janus/lib/janus/loggers" # External loggers folder
....}
  • SSL certs for DTLS can also be specified under certificates
  • Restricting media ports between a range . Comes in handy when u have to selectively open ports ona cloud instance such as AWS instance
media: {
        ipv6 = false
        #min_nack_queue = 500
        rtp_port_range = "20000-40000"
        #dtls_mtu = 1200
        #no_media_timer = 1
        #slowlink_threshold = 4
        #twcc_period = 100
        #dtls_timeout = 500
  • changing NAT for STUN/TURN servers to gather ICE

using 1:1 NAT( suited to Amzon EC2) requires specifying public address

nat_1_1_mapping = "1.1.1.1"
  • To change transport http , set http to true from false

goto installation location for janus config

cd /opt/janus/etc/janus/
> vi /opt/janus/etc/janus/janus.transport.http.jcfg

general: {
    #events = true                 # Whether to notify event handlers about transport events (default=true)
    json = "indented"              # Whether the JSON messages should be indented (default),
                                   # plain (no indentation) or compact (no indentation and no spaces)
    base_path = "/janus"           # Base path to bind to in the web server (plain HTTP only)
    http = true                    # Whether to enable the plain HTTP interface
    port = 8088                    # Web server HTTP port
    #interface = "eth0"            # Whether we should bind this server to a specific interface only
    #ip = "x.x.x.x"                # Whether we should bind this server to a specific IP address (v4 or v6) only
    https = true                   # Whether to enable HTTPS (default=false)
    secure_port = 8089             # Web server HTTPS port, if enabled
    #secure_interface = "eth0"     # Whether we should bind this server to a specific interface only
    #secure_ip = "192.168.0.1"     # Whether we should bind this server to a specific IP address (v4 or v6) only
    #acl = "127.,192.168.0."       # Only allow requests coming from this comma separated list of addresses
}

Change path for certs and key pem files

> vi janus.jcfg

certificates: {
        cert_pem = "/home/ubuntu/ssl/cert.pem"
        cert_key = "/home/ubutu/ssl/key.pem"
        #cert_pwd = "secretpassphrase"
        #dtls_accept_selfsigned = false
        #dtls_ciphers = "your-desired-openssl-ciphers"
        #rsa_private_key = false
      #ciphers = "PFS:-VERS-TLS1.0:-VERS-TLS1.1:-3DES-CBC:-ARCFOUR-128"
}

There are options for other ciphers and passphrass , leave them for now.

  • To change transport ws for websocket
general: {
        #events = true            # Whether to notify event handlers about transport events (default=true)
        json = "indented"         # Whether the JSON messages should be indented (default),
                                  # plain (no indentation) or compact (no indentation and no spaces)
        #pingpong_trigger = 30    # After how many seconds of idle, a PING should be sent
        #pingpong_timeout = 10    # After how many seconds of not getting a PONG, a timeout should be detected

        ws = true                 # Whether to enable the WebSockets API
        ws_port = 8188            # WebSockets server port
        #ws_interface = "eth0"    # Whether we should bind this server to a specific interface only
        #ws_ip = "192.168.0.1"    # Whether we should bind this server to a specific IP address only
        wss = true                # Whether to enable secure WebSockets
        wss_port = 8989           # WebSockets server secure port, if enabled
        #wss_interface = "eth0"   # Whether we should bind this server to a specific interface only
        #wss_ip = "192.168.0.1"   # Whether we should bind this server to a specific IP address only
        #ws_logging = "err,warn"  # libwebsockets debugging level as a comma separated list of things
                                  # to debug, supported values: err, warn, notice, info, debug, parser,
                                  # header, ext, client, latency, user, count (plus 'none' and 'all')
        #ws_acl = "127.,192.168.0." # Only allow requests coming from this comma separated list of addresses
}

Simillar to http transport conf above , also update the certs section with valid path for ssl certs

Check

Running ports check ( http )

> sudo lsof -i  | grep janus
janus     26450          ubuntu    7u  IPv6 418550      0t0  UDP *:rfe 
janus     26450          ubuntu    8u  IPv6 418551      0t0  UDP *:5004 
janus     26450          ubuntu   17u  IPv6 418557      0t0  TCP *:omniorb (LISTEN)
janus     26450          ubuntu   20u  IPv6 672518      0t0  TCP *:8089 (LISTEN)
janus     26450          ubuntu   24u  IPv4 672519      0t0  TCP *:8188 (LISTEN)
janus     26450          ubuntu   25u  IPv4 672520      0t0  TCP *:8989 (LISTEN) 

Janus INFO

Going to deployed janus URL like http://x.x.x.x:8088/janus/info

   "janus": "server_info",
   "transaction": "rGuo8HNI4wu",
   "name": "Janus WebRTC Gateway",
   "version": 26,
   "version_string": "0.2.6",
   "author": "Meetecho s.r.l.",
   "commit-hash": "not-a-git-repo",
   "compile-time": "Wed Feb 28 07:02:15 UTC 2018",
   "log-to-stdout": true,
   "log-to-file": false,
   "data_channels": false,
   "session-timeout": 60,
   "server-name": "MyJanusInstance",
   "local-ip": "x.x.x.x",
   "ipv6": false,
   "ice-lite": false,
   "ice-tcp": false,
   "api_secret": false,
   "auth_token": false,
   "event_handlers": false,
   "transports": {
      "janus.transport.http": {
         "name": "JANUS REST (HTTP/HTTPS) transport plugin",
         "author": "Meetecho s.r.l.",
         "description": "This transport plugin adds REST (HTTP/HTTPS) support to the Janus API via libmicrohttpd.",
         "version_string": "0.0.2",
         "version": 2
      },
      "janus.transport.websockets": {
         "name": "JANUS WebSockets transport plugin",
         "author": "Meetecho s.r.l.",
         "description": "This transport plugin adds WebSockets support to the Janus API via libwebsockets.",
         "version_string": "0.0.1",
         "version": 1
      }
   },
   "events": {},
   "plugins": {
      "janus.plugin.voicemail": {
         "name": "JANUS VoiceMail plugin",
         "author": "Meetecho s.r.l.",
         "description": "This is a plugin implementing a very simple VoiceMail service for Janus, recording Opus streams.",
         "version_string": "0.0.6",
         "version": 6
      },
      "janus.plugin.audiobridge": {
         "name": "JANUS AudioBridge plugin",
         "author": "Meetecho s.r.l.",
         "description": "This is a plugin implementing an audio conference bridge for Janus, mixing Opus streams.",
         "version_string": "0.0.10",
         "version": 10
      },
      "janus.plugin.echotest": {
         "name": "JANUS EchoTest plugin",
         "author": "Meetecho s.r.l.",
         "description": "This is a trivial EchoTest plugin for Janus, just used to showcase the plugin interface.",
         "version_string": "0.0.7",
         "version": 7
      },
      "janus.plugin.recordplay": {
         "name": "JANUS Record&amp;Play plugin",
         "author": "Meetecho s.r.l.",
         "description": "This is a trivial Record&amp;Play plugin for Janus, to record WebRTC sessions and replay them.",
         "version_string": "0.0.4",
         "version": 4
      },
      "janus.plugin.textroom": {
         "name": "JANUS TextRoom plugin",
         "author": "Meetecho s.r.l.",
         "description": "This is a plugin implementing a text-only room for Janus, using DataChannels.",
         "version_string": "0.0.2",
         "version": 2
      },
      "janus.plugin.videoroom": {
         "name": "JANUS VideoRoom plugin",
         "author": "Meetecho s.r.l.",
         "description": "This is a plugin implementing a videoconferencing SFU (Selective Forwarding Unit) for Janus, that is an audio/video router.",
         "version_string": "0.0.9",
         "version": 9
      },
      "janus.plugin.sipre": {
         "name": "JANUS SIPre plugin",
         "author": "Meetecho s.r.l.",
         "description": "This is a simple SIP plugin for Janus (based on libre instead of Sofia), allowing WebRTC peers to register at a SIP server and call SIP user agents through the gateway.",
         "version_string": "0.0.1",
         "version": 1
      },
      "janus.plugin.videocall": {
         "name": "JANUS VideoCall plugin",
         "author": "Meetecho s.r.l.",
         "description": "This is a simple video call plugin for Janus, allowing two WebRTC peers to call each other through the gateway.",
         "version_string": "0.0.6",
         "version": 6
      },
      "janus.plugin.streaming": {
         "name": "JANUS Streaming plugin",
         "author": "Meetecho s.r.l.",
         "description": "This is a streaming plugin for Janus, allowing WebRTC peers to watch/listen to pre-recorded files or media generated by gstreamer.",
         "version_string": "0.0.8",
         "version": 8
      },
      "janus.plugin.nosip": {
         "name": "JANUS NoSIP plugin",
         "author": "Meetecho s.r.l.",
         "description": "This is a simple RTP bridging plugin that leaves signalling details (e.g., SIP) up to the application.",
         "version_string": "0.0.1",
         "version": 1
      },
      "janus.plugin.sip": {
         "name": "JANUS SIP plugin",
         "author": "Meetecho s.r.l.",
         "description": "This is a simple SIP plugin for Janus, allowing WebRTC peers to register at a SIP server and call SIP user agents through the gateway.",
         "version_string": "0.0.7",
         "version": 7
      }
   }
}

ECHO Test

An Echo test is part of Janus and can be done via reached via deployed server url https://x.x.x.x:8084/echotest.html

For a valid SDP message notice the contact headers in chrome://webrtc-internals

Local Description (mungled)

O line represents origin

type: offer, sdp: v=0
o=- 1331622865522329207 2 IN IP4 127.0.0.1


Audio Media stream in m line 

m=audio 9 UDP/TLS/RTP/SAVPF 111 103 104 9 0 8 106 105 13 110 112 113 126
c=IN IP4 0.0.0.0


Video media stream in m line 

m=video 9 UDP/TLS/RTP/SAVPF 96 97 98 99 100 101 102 122 127 121 125 107 108 109 124 120 123
c=IN IP4 0.0.0.0


Data

m=application 9 UDP/DTLS/SCTP webrtc-datachannel
c=IN IP4 0.0.0.0

Remote Description

Origin Line

type: answer, sdp: v=0
o=- 6397148042001786590 2 IN IP4 54.193.51.199

Audio Stream

m=audio 9 UDP/TLS/RTP/SAVPF 111 9 0 8 106 105 13 110 112 113
c=IN IP4 54.193.51.199

Video Stream

m=video 9 UDP/TLS/RTP/SAVPF 96 98 100 102 127 125 108 97 99 101 122 121 107 109
c=IN IP4 54.193.51.199

Data 

m=application 0 UDP/DTLS/SCTP 0
c=IN IP4 54.193.51.199

VideoCall – https://x.x.x.x:8084/videocalltest.html

Run

./opt/janus/bin/janus

Plugin (above ) and then procceeds to join the room ( screenshot below)

After this Janus procced to do JSEP offer / answer signalling with ICE checks and then does keepalive checks for the duraion of the session .

Stream Types

Unicast

a=sendonly
a=recvonly
a=sendrecv
a=inactive

Simulcast

https://x.x.x.x:8084/videocalltest.html?simulcast=true

LD Libbary Path Exception

If you see an missing encryption exception , start janus with LD_LIBRARY_PATH

export LD_LIBRARY_PATH=/usr/lib && /opt/janus/bin/janus --debug-level=7 --stun-server=stun.l.google.com:19302 --event-handlers --full-trickle

ICE resolution in Runtime

Trickle ICE Command Line params give console output as

[janus.cfg]
    general: {
        debug_level: 7
    }
    certificates: {
    }
    nat: {
        stun_server: stun.l.google.com
        stun_port: 19302
        full_trickle: true
    }
    media: {
    }
    transports: {
    }
    plugins: {
    }
    events: {
        broadcast: yes
    }
    loggers: {
    }

With NAT 1:1 mapping

export LD_LIBRARY_PATH=/usr/lib && /opt/janus/bin/janus --debug-level=7 --nat-1-1=54.193.51.199 --stun-server=stun.l.google.com:19302 --rtp-port-range=20000-50000 

1 to 1 NAT mpapping coordinates with amazon ec2

[janus.cfg]
    general: {
        debug_level: 7
    }
    certificates: {
    }
    nat: {
        nat_1_1_mapping: 54.193.51.199
    }
    media: {
        rtp_port_range: 20000-50000
    }
    transports: {
    }
    plugins: {
    }
    events: {
    }
    loggers: {
    }

WebRTC Client for Janus System

Test client

Using the html sample clients

cd html
admin.html            citeus.html      e2etest.html   index.html      nosiptest.html          siptest.html        textroomtest.html   voicemailtest.html audiobridgetest.html  demos.html       echotest.html  multiopus.html  recordplaytest.html     streamingtest.html  videocalltest.html  vp9svctest.html canvas.html           devicetest.html  footer.html    navbar.html     screensharingtest.html  support.html        videoroomtest.html

check lsb release and then Install Nodejs to host client page

>> lsb_release -a
curl -sL https://deb.nodesource.com/setup_15.x | sudo -E bash -
sudo apt-get install -y nodejs

Http WebServer

npm init
npm install http-server
node_modules/http-server/bin/http-server

To be able to compile native addons from npm you’ll need to install the development tools:

sudo apt install build-essential

open the client in webrtc supported browser at http://x.x.x.x:8080/videoroomtest.html

If you see a issues

 No WebRTC media anymore; 0x7fbe20001a40 0x7fbe20002440
 WebRTC resources freed; 0x7fbe20001a40 0x7fbe20001320
 Handle and related resources freed; 0x7fbe20001a40 0x7fbe20001320

Then it is likley a NAT issues and you should look at jcfg config file to see whether the interface is specified corectly

# Generic settings
interface = "x.x.x.x"                                     # Interface to use (will be used in SDP)
server_name = "WebrtcMCUJanus"                                  # Public name of this Janus instance

Security consideration before taking janus live

Hide the dependencies

hide_dependencies = true  

By default, a call to the “info” endpoint of either the Janus or Admin API now als returns the versions of the main dependencies (e.g., libnice, libsrtp, which crypto library is in use and so on). Should you want that info not to be disclose, set ‘hide_dependencies’ to true.

Common spam attack. source https://groups.google.com/g/meetecho-janus/c/IcJd3e4V1F8

Issues : Janus is throwing an error Invalid url /ws/v1/cluster/apps/new-application

Possible solution : changing port of http transport

References

To read more about Media Archietctures and topologies such as point-point , point-to-multipoint , multicast , translators, mixers and SFU goto :

Media Architecture, RTP topologies

With the sudden onset of Covid-19 and building trend of working-from-home , the demand for building scalable conferncing solution and virtual meeting room has skyrocketed . Here is my advice if you are building a auto- scalable conferencing solution

To read more on the topologies of conferencing systems ( Mesh vs Star , Unicast vs Multicast and SVC) read :

SIP conferencing and Media Bridges

SIP is the most popular signalling protocol in VOIP ecosystem. It is most suited to a caller-callee scenario , yet however supporting scalable conferences on VOIP is a market demand. It is desired that SIP must for multimedia stream but also provide conference control for building communication and collaboration apps for new and customisable solutions.

Gstreamer

GStreamer ( LGPL )ia a media handling library written in C for applicatioan such as streaming , recording, playback , mixing and editing attributes etc. Even enhnaced applicaiosn such as tsrancoding , media ormat conversion , streaming servers for embeeded devices ( read more about Gstreamer in RPi in my srticle here).
It encompases various codecs, filters and is modular with plugins developement to enhance its capabilities. Media Streaming application developers use it as part of their framework at either the broadcaster’s end or as media player.

gst-launch-1.0 videotestsrc ! videoconvert ! autovideosink

More detailed reading :

GStreamer-1.8.1 rtsp server and client on ubuntu – Install and configuration for a RTSP Streaming server and Client https://telecom.altanai.com/2016/05/20/gstreamer-1-8-1-rtsp-server-and-client-on-ubuntu/

crtmpserver + ffmpeg –

https://telecom.altanai.com/2016/06/19/crtmpserver-ffmpeg

Streaming / broadcasting Live Video call to non webrtc supported browsers and media players

 attempts of streaming / broadcasting Live Video WebRTC call to non WebRTC supported browsers and media players such as VLC , ffplay , default video player in Linux etc .

https://telecom.altanai.com/2015/02/17/streaming-broadcasting-live-video-call-to-non-webrtc-supported-browsers-and-media-players/

continue : Streaming / broadcasting Live Video call to non webrtc supported browsers and media players

httontinuation to the attempts / outcomes and problems in building a WebRTC to RTP media framework that successfully stream / broadcast WebRTC content to non webrtc supported browsers ( safari / IE ) / media players ( VLC )

https://telecom.altanai.com/2015/02/26/continue-streaming-broadcasting-live-video-call-to-non-webrtc-supported-browsers-and-media-players/

TO continue with basics of gstreamer keep reading

To list all packages of Gstreamer

pkg-config --list-all | grep gstreamer
  • gstreamer-gl-1.0 GStreamer OpenGL Plugins Libraries – Streaming media framework, OpenGL plugins libraries
  • gstreamer-bad-video-1.0GStreamer bad video library – Bad video library for GStreamer elements
  • gstreamer-tag-1.0 GStreamer Tag Library – Tag base classes and helper functions
  • gstreamer-bad-base-1.0 GStreamer bad base classes – Bad base classes for GStreamer elements
  • gstreamer-net-1.0GStreamer networking library – Network-enabled GStreamer plug-ins and clocking
  • gstreamer-sdp-1.0 GStreamer SDP Library – SDP helper functions
  • gstreamer-1.0 GStreamer – Streaming media framework
  • gstreamer-bad-audio-1.0 GStreamer bad audio library, uninstalled – Bad audio library for GStreamer elements, Not Installedgstreamer-allocators-1.0 GStreamer Allocators Library – Allocators implementation
  • gstreamer-player-1.0 GStreamer Player – GStreamer Player convenience library
  • gstreamer-insertbin-1.0 GStreamer Insert Bin – Bin to automatically and insertally link elements
  • gstreamer-plugins-base-1.0 GStreamer Base Plugins Libraries – Streaming media framework, base plugins libraries
  • gstreamer-vaapi-glx-1.0 GStreamer VA-API (GLX) Plugins Libraries – Streaming media framework, VA-API (GLX) plugins librariesgstreamer-codecparsers-1.0 GStreamer codec parsers – Bitstream parsers for GStreamer elementsgstreamer-base-1.0 GStreamer base classes – Base classes for GStreamer elements
  • gstreamer-app-1.0 GStreamer Application Library – Helper functions and base classes for application integration
  • gstreamer-vaapi-drm-1.0 GStreamer VA-API (DRM) Plugins Libraries – Streaming media framework, VA-API (DRM) plugins librariesgstreamer-check-1.0 GStreamer check unit testing – Unit testing helper library for GStreamer modules
  • gstreamer-vaapi-1.0 GStreamer VA-API Plugins Libraries – Streaming media framework, VA-API plugins libraries
  • gstreamer-controller-1.0 GStreamer controller – Dynamic parameter control for GStreamer elements
  • gstreamer-video-1.0 GStreamer Video Library – Video base classes and helper functions
  • gstreamer-vaapi-wayland-1.0 GStreamer VA-API (Wayland) Plugins Libraries – Streaming media framework, VA-API (Wayland) plugins libraries
  • gstreamer-fft-1.0 GStreamer FFT Library – FFT implementation
  • gstreamer-mpegts-1.0 GStreamer MPEG-TS – GStreamer MPEG-TS support
  • gstreamer-pbutils-1.0 GStreamer Base Utils Library – General utility functions
  • gstreamer-vaapi-x11-1.0 GStreamer VA-API (X11) Plugins Libraries – Streaming media framework, VA-API (X11) plugins libraries
  • gstreamer-rtp-1.0 GStreamer RTP Library – RTP base classes and helper functions
  • gstreamer-rtsp-1.0 GStreamer RTSP Library – RTSP base classes and helper functions
  • gstreamer-riff-1.0 GStreamer RIFF Library – RIFF helper functions
  • gstreamer-audio-1.0 GStreamer Audio library – Audio helper functions and base classes
  • gstreamer-plugins-bad-1.0 GStreamer Bad Plugin libraries – Streaming media framework, bad plugins libraries
  • gstreamer-rtsp-server-1.0 gst-rtsp-server – GStreamer based RTSP server

At the time of writing this article Gstreamer an much early version in 1.X , which was newer than its then stable version 0.x. Since then the library has updated many fold. summarising release highlights for major versions as the blog was updated over time .

Project : Making and IP survillance system using gstreamer and Janus

To build a turn-key easily deployable surveillance solution 

Features :

  1. Paring of Android Mobile with box
  2. Live streaming from Box to Android
  3. Video Recording inside the  box
  4. Auto parsing of recorded video around motion detection 
  5. Event listeners 
  6. 2 way audio
  7. Inbuild Media Control Unit
  8. Efficient use of bandwidth 
  9. Secure session while live-streaming

Modules

  1. Authentication ( OTP / username- password)
  2. Livestreaming on Opus / vp8 
  3. Session Security and keepalives for live-streaming sessions
  4. Sync local videos to cloud storage 
  5. Record and playback with timeline and events 
  6. Parsing and restructuring video ( transcoding may also be required ) 
  7. Coturn server for NAT and ICE
  8. Web platform on box ( user interface )+ NoSQL
  9. Web platform on Cloud server ( Admin interface )+ NoSQL
  10.  REST APIs for third party add-ons ( Node based )
  11. Android demo app for receiving the live stream and feeds

Varrying experiments and working gstreamer commands

Local Network Stream 

To create /dev/video0

modprobe bcm2835-v4l2

To stream on rtspserver using rpicamsrc using h264 parse

./gst-rtsp-server-1.4.4/examples/test-launch --gst-debug=2 '(rpicamsrc num-buffers=5000 ! 'video/x-h264,width=1080,height=720,framerate=30/1' ! h264parse ! rtph264pay name=pay0 pt=96 )'

./test-launch “( tcpclientsrc host=127.0.0.1 port=5000 ! gdpdepay ! rtph264pay name=pay0 pt=96 )”

pipe raspivid to tcpserversink

raspivid -t 0 -w 800 -h 600 -fps 25 -g 5 -b 4000000 -vf -n -o - | gst-launch-1.0 -v fdsrc ! h264parse ! gdppay ! tcpserversink host=127.0.0.1 port=5000;

Stream Video over local Network with 15 fps

raspivid -n -ih -t 0 -rot 0 -w 1280 -h 720 -fps 15 -b 1000000 -o - | nc -l -p 5001

streaming video over local network with 30FPS and higher bitrate

raspivid -n -t 0 -rot 0 -w 1920 -h 1080 -fps 30 -b 5000000 -o - | nc -l -p 5001

Recording

Audio record to file
Using arecord :

arecord -D plughw:1 -c1 -r 48000 -f S16_LE -t wav -v file.wav;

Using pulse :
pulseAudio -D

gst-launch-1.0 -v pulsesrc device=hw:1 volume=8.0 ! audio/x-raw,format=S16LE ! audioconvert ! voaacenc bitrate=48000 ! aacparse ! flvmux ! filesink location = "testaudio.flv";

Video record to file ( mpg)

gst-launch-1.0 -e rpicamsrc bitrate=500000 ! 'video/x-h264,width=640,height=480’ ! mux. avimux name=mux ! filesink location=testvideo2.mpg;

Video record to file ( flv )

gst-launch-1.0 -e rpicamsrc bitrate=500000 ! video/x-h264,width=320,height=240,framerate=10/1 ! h264parse ! flvmux ! filesink location="testvieo.flv";

Video record to file ( h264)
gst-launch-1.0 -e rpicamsrc bitrate=500000 ! filesink location=”raw3.h264″;

Video record to file ( mp4)

gst-launch-1.0 -e rpicamsrc bitrate=500000 ! video/x-h264,width=320,height=240,framerate=10/1 ! h264parse ! mp4mux ! filesink location=video.mp4;

Audio + Video record to file ( flv)

gst-launch-1.0 -e /
rpicamsrc bitrate=500000 ! /
video/x-h264,width=320,height=240,framerate=10/1 ! h264parse ! muxout. /
pulsesrc volume=8.0 ! /
queue ! audioconvert ! voaacenc bitrate=65536 ! aacparse ! muxout. /
flvmux name=muxout streamable=true ! filesink location ='test44.flv';

Audio + Video record to file ( flv) using pulsesrc

gst-launch-1.0 -v --gst-debug-level=3 pulsesrc device="alsa_input.platform-asoc-simple-card.0.analog-stereo" volume=5.0 mute=FALSE ! audio/x-raw,format=S16LE,rate=48000,channels=1 ! audioresample ! audioconvert ! voaacenc ! aacparse ! flvmux ! filesink location="voicetest.flv";

Audio + Video record to file (mp4)

gst-launch-1.0 -e /
rpicamsrc bitrate=500000 ! /
video/x-h264,width=320,height=240,framerate=10/1 !s h264parse ! muxout. /
pulsesrc volume=4.0 ! /
queue ! audioconvert ! voaacenc ! muxout. /
flvmux name=muxout streamable=true ! filesink location = 'test224.mp4';

Streaming

stream raw Audio over RTMP to srtmpsink

gst-launch-1.0 pulsesrc device=hw:1 volume=8.0 ! /
audio/x-raw,format=S24LE ! audioconvert ! voaacenc bitrate=48000 ! aacparse ! flvmux ! rtmpsink location = “rtmp://192.168.0.3:1935/live/test”;

stream AACpparse Audio over RTMP to srtmpsink

gst-launch-1.0 -v --gst-debug-level=3 pulsesrc device="alsa_input.platform-asoc-simple-card.0.analog-stereo" volume=5.0 mute=FALSE ! audio/x-raw,format=S16LE,rate=48000,channels=1 ! audioresample ! audioconvert ! voaacenc ! aacparse ! flvmux ! rtmpsink location="rtmp://www.altani.com:1935/voice/1/test";

stream Video over RTMP

gst-launch-1.0 -e rpicamsrc bitrate=500000 ! /
video/x-h264,width=320,height=240,framerate=6/1 ! h264parse ! /
flvmux ! rtmpsink location = ‘rtmp://52.66.125.31:1935/live/test live=1’;

stream Audio + video over RTMP from rpicamsrc , framerate 10

gst-launch-1.0 rpicamsrc bitrate=500000 ! video/x-h264,width=320,height=240,framerate=10/1 ! h264parse ! muxout. pulsesrc volume=8.0 ! queue ! audioconvert ! voaacenc bitrate=65536 ! aacparse ! muxout. flvmux name=muxout streamable=true ! rtmpsink location ='rtmp://www.altanai.com/live/test44';

stream Audio + video over RTMP from rpicamsrc , framerate 30

gst-launch-1.0 rpicamsrc bitrate=500000 ! video/x-h264,width=1280,height=720,framerate=30/1 ! h264parse ! muxout. pulsesrc ! queue ! audioconvert ! voaacenc bitrate=65536 ! aacparse ! muxout. flvmux name=muxout ! queue ! rtmpsink location ='rtmp://www.altanai.com/live/test44';

VOD ( video On Demand )

Stream h264 file over RTMP

gst-launch-1.0 -e filesrc location="raw3.h264" ! video/x-h264 ! h264p
arse ! flvmux ! rtmpsink location = 'rtmp://www.altanai.com/live/test';

Stream flv file over RTMP

gst-launch-1.0 -e filesrc location=”testvieo.flv” ! /
video/x-h264,width=320,height=240,framerate=10/1 ! h264parse ! /
flvmux ! rtmpsink location = 'rtmp://192.168.0.3:1935/live/test';

Github Repo for Livestreaming

https://github.com/altanai/Livestreaming

Contains code for Android and ios Publishers , players on various platforms including HLS and Flash , streamings servers , Wowza playing mosules , webrtc broadcast

Gstreamer 1.8.0 – 24 March 2016

Features Hardware-accelerated zero-copy video decoding on Android

New video capture source for Android using the android.hardware.Camera API

Windows Media reverse playback support (ASF/WMV/WMA)

tracing system provides support for more sophisticated debugging tools

high-level GstPlayer playback convenience API

Initial support for the new Vulkan API

Improved Opus audio codec support: Support for more than two channels; MPEG-TS demuxer/muxer can handle Opus; sample-accurate encoding/decoding/transmuxing with Ogg, Matroska, ISOBMFF (Quicktime/MP4), and MPEG-TS as container; new codec utility functions for Opus header and caps handling in pbutils library. The Opus encoder/decoder elements were also moved to gst-plugins-base (from -bad), and the opus RTP depayloader/payloader to -good.

Asset proxy support in the GStreamer Editing Services

GStreamer 1.16.0 – 19 April 2019.

GStreamer WebRTC stack gained support for data channels for peer-to-peer communication based on SCTP, BUNDLE support, as well as support for multiple TURN servers.

AV1 video codec support for Matroska and QuickTime/MP4 containers and more configuration options and supported input formats for the AOMedia AV1 encoder

Closed Captions and other Ancillary Data in video

planar (non-interleaved) raw audio

GstVideoAggregator, compositor and OpenGL mixer elements are now in -base

New alternate fields interlace mode where each buffer carries a single field

WebM and Matroska ContentEncryption support in the Matroska demuxer

new WebKit WPE-based web browser source element

Video4Linux: HEVC encoding and decoding, JPEG encoding, and improved dmabuf import/export

Hardware-accelerated Nvidia video decoder gained support for VP8/VP9 decoding, whilst the encoder gained support for H.265/HEVC encoding.

Improvements to the Intel Media SDK based hardware-accelerated video decoder and encoder plugin (msdk): dmabuf import/export for zero-copy integration with other components; VP9 decoding; 10-bit HEVC encoding; video post-processing (vpp) support including deinterlacing; and the video decoder now handles dynamic resolution changes.

ASS/SSA subtitle overlay renderer can now handle multiple subtitles that overlap in time and will show them on screen simultaneously

Meson build feature-complete (with the exception of plugin docs) and it is now the recommended build system on all platforms. The Autotools build is scheduled to be removed in the next cycle.

GStreamer Rust bindings and Rust plugins module

GStreamer Editing Services allows directly playing back serialized edit list with playbin or (uri)decodebin

References :

https://gstreamer.freedesktop.org