Document chapter 01

* the routing structure
* the building blocks inside Element-Call
This commit is contained in:
Ralf Zerres
2024-10-17 12:41:08 +02:00
parent aec8acee46
commit 36bb3d6b8a
14 changed files with 154 additions and 9 deletions

View File

@@ -7,8 +7,11 @@
# Getting started # Getting started
- [Getting Started](ch01-00-getting-started.md) - [Getting Started](ch01-00-getting-started.md)
- [The building blocks](ch01-01-building-blocks.md) - [The routing structures](ch01-01-routing-structures.md)
- [Hello Element-Call!](ch01-02-element-call-hello.md) - [The building blocks](ch01-02-building-blocks.md)
<!--
- [Hello Element-Call!](ch01-03-element-call-hello.md)
-->
- [Installation](ch02-00-installation.md) - [Installation](ch02-00-installation.md)

View File

@@ -3,5 +3,5 @@
Lets start your Element-Call journey! Theres a lot to learn, but every journey starts Lets start your Element-Call journey! Theres a lot to learn, but every journey starts
somewhere. In this chapter, well discuss: somewhere. In this chapter, well discuss:
* WebRTC bases routing structures
* The building blocks of Element-Call * The building blocks of Element-Call
* Installing Element-Call

View File

@@ -1,4 +0,0 @@
## Building blocks
[element_call_building_blocks]: https://gitea.networkx.de/rzerres/element-call/book/blob/main/src/img/element-call_building_blocks.png

View File

@@ -0,0 +1,55 @@
## WebRTC bases routing structures
The following image visualize the concepts of actively used routing
structures inside a RTC applications.
![voip routing structures][voip_routing_structure]
Historically `Elememnt-Call` did implement an infrastructure, where
all participants were fully meshed. That means all participants had a
direct peer to each other in a `Mesh`. This structure does work quite well with a
low number of call partners (e.g 1:1 sessions). Clearly this structure
is totally inefficient and collapsing, as soon as the number of
participants rises: The needed number of streams that have to be
synchronized are increasing exponentioally.
Most `commercial solutions` overcome this bottleneck utilizing a
Multipoint Connection Unit (`MCU`): Each participant of the call is
directly connected to the controlling MCU. The MCU will consolidate
all streams and has only one stream to each participant. It is able to linearly scale.
MCU routing has disadvantages and shortcommings too.
* You can't assign different egress parameters from the MCU to
individual participant streams
* A single MCU can't handle distributed structure
Therefore `Element-Call` has choosen to implement the service on top of a
Selective Forward Unit (`SFU`) capable backend:
![Matrix structures][matrix_structure]
Each participant will only send in one stream to the choosen
`SFU`. The number of egress streams can scale linearly, comparable to
the concept used with an MCU. But in contrast to MCU based
communication clients insede the MatrixRTC are able to dynamicaly
advertise to their SFU what ingress streams they are interested in.
Here are some commen szenarios:
* I'm only interested to get participant A, B, C, E, G but not D and F
* Please only send high resolutions for the speaker and reduce the
bitrate for all other participants
* Change my own egress bitrate to a given value
On top of this, the nature of a Matrix based communication makes use of a
distributed infrastructure. Within MatrixRTC that allows communications
* between different involved SFU's
* Require and handle E2EE meetings for all participants
* Authenticate matrix accounts as well as guest accounts inside a call
![Matrix SFU structures][matrix_sfu_structure]
[matrix_structure]: ./img/matrix_structure.webp
[matrix_sfu_structure]: ./img/matrix_sfu_structure.png
[voip_routing_structure]: ./img/voip_routing_structures.png

View File

@@ -0,0 +1,91 @@
## Building blocks
For good reasons `Element-Call` is subdevided into logical components that encapsulate given functionality
* The Backend
* The reverse Proxy
* The Authentication service
* The Frontend
All this components have to be orchestrated to make up this realtime application. Let's have a look how they interact:
![Element-call structure][element_call_structure]
[element_call_structure]: ./img/element-call-structure.svg
### Backend
The MatrixRTC functionality is handled via [LiveKit][livekit_source].
Livekit is very versatile and flexible. It offers a clean API which
makes it an ideal fit to be used from the integration service.
[livekit_source]: https://github.com/livekit
### Reverse Proxy
In computer networks, a reverse proxy or surrogate server is a proxy
server that appears to any client to be an ordinary web server, but in
reality merely acts as an intermediary that forwards the client's
requests to one or more ordinary web servers. Reverse proxies
help increase scalability, performance, resilience, and security.
![Reverse-Proxy Service][reverse_proxy_service]
For example, your server-domain is only accessible via one official ip
address. But you like to offer multiple services that require secure
web traffik (https). You have to assign officliy signed certificates to this web server, but also need a proxy that, that can distinguish
which backend will handle the data exchange (rules, fqdn).
Following list is an non-exauthive list of popular proxy
implementation that may be run as reverse proxys:
* [HAProxy][haproxy_source]
* [NGINX][nginx_source]
* [traefik][traefik_source]
`Element-Call` will need to use such a reverse proxy, since it needs to re-route service traffik to other components that need to be exposed to the internet (explicitely: livekit, lifekit-jwt-service).
[haproxy_source]: https://github.com/haproxy/haproxy
[nginx_source]: https://github.com/nginx
[reverse_proxy_service]: ./img/reverse_proxy_structure.png
[traefik_source]: https://github.com/traefik/traefik
### Frontend
The `Element-Call` frontend handles the login of participants. You
can choose matrix account that is already registered on your
homeserver, or connect as a guest user to an existing call.
You may obtain the URL to the existing call from any room members.
![Element-Call brower login][element_call_browser_login]
The source code for the frontend is maintained at `github` in the
[Element-Call][element_call_source] repository.
[element_call_source]: https://github.com/element-hq/element-call
[element_call_browser_login]: ./img/element-call-browser-login.png
### Authentication service
After a participant has registerd himself via the `element-call`
frontend (as an existing matrix account or a guest user),
[websockets][websockets_service] are used to forward and manage the
required data via Json Web Tokens (`JWT`) to the livekit backend. This
allows to keep any communication secure, which is an elementary
request for E2EE calls.
![websocket_connection`][websocket_connection]
This job is handled from the
[`livekit_jwt_service`][livekit_jwt_service], that will forward the
correct tokens to the SFU endpoint inside the livekit instance the
user is connected to.
[livekit_jwt_service]: https://github.com/element-hq/lk-jwt-service
[websocket_connection]: ./img/websocket_connection.png
[websockets_service]: https://en.wikipedia.org/wiki/WebSocket

Binary file not shown.

Before

Width:  |  Height:  |  Size: 17 KiB

After

Width:  |  Height:  |  Size: 188 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 21 MiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 855 KiB

After

Width:  |  Height:  |  Size: 2.3 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 188 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 51 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 28 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

View File

@@ -1,8 +1,8 @@
# Element Call # Element-Call
![Element-Call][element_call] ![Element-Call][element_call]
[element_call]: https://gitea.networkx.de/rzerres/element-call-book/book/blob/main/src/img/element-call.png [element_call]: https://gitea.networkx.de/rzerres/element-call-book/blob/main/src/img/element-call.png
*annotated and documented by Ralf Zerres and all contributers* *annotated and documented by Ralf Zerres and all contributers*