General Information
This guide helps to install Synapse Matrix Server, Riot Web UI, coturn Turn Server, Dimension integration server, jitsi conferencing system and the matrix user/room admin tool. It assumes there is an apache web-server serving requests from the outside world.
None of the components or the information is originally mine. This is just an attempt to summarize all together in a long how-to.
Note 1: I will be installing all the docker packages at
/home/*Note 2:
server.key,server.crtandca.crtare respectively private key, public key, and certificate-authority certificate to be used by components. I usually have a wildcard certificate for all my subdomains. but if you don’t want to use such a certificate, then you need separate certificates when creating reverse-proxies or configuring your turn-server
Before we begin
You can consider installing portainer to ease the management of dockers. Unfortunately, the docker-compose files cannot be used directly in portainer, as it doesn’t support version: '3' and above. Nevertheless, it provides a nice UI to see the status of each container, to manage it, and to check out the logs.
This could (probably) be used to install portainer container. It will start a web-UI on port 9000 of the docker machine, through which it’s possible to restart, recreate, and modify containers, as well as defining new containers, seeing log files and performance statistics etc.
- Installation path:
/home/portainer - Don’t forget to map
docker.sockto/var/run/docker.sock - Ports:
9000for UI
Note: Please consider security factors when exposing this container to the internet, as any person with administrative right can install and modify your containers.
version: '3'
services:
portainer:
image: portainer/portainer
container_name: portainer
restart: always
command: -H unix:///var/run/docker.sock
ports:
- "9000:9000"
volumes:
- /var/run/docker.sock:/var/run/docker.sock
- /home/portainer/data:/data
- /home/portainer/shared:/shared
environment:
- TZ=${TZ}
Configure Turn Server
Let’s start with coturn TURN-Server. it’s independent of other components and can be used for several different purposes.
You can read more about the functionality of TURN and STUN servers here: https://blog.ivrpowers.com/post/technologies/what-is-stun-turn-server/
- Original Documentation: https://github.com/instrumentisto/coturn-docker-image
- Installation Path:
/home/coturn - needed ports:
3478,5349,49100-49200 - docker image:
instrumentisto/coturn network_modeis set tohostin order to ease the mapping of ports from the container to the outside world.- Configuration files are stored in
{installation-path}/conf - SSL keys and certificates are to be stored in
{installation-path}/keys docker-compose.ymlas provided
#/home/coturn/docker-compose.yml
version: '3'
services:
coturn:
restart: unless-stopped
container_name: coturn
image: instrumentisto/coturn
network_mode: host
volumes:
- /home/coturn/conf:/etc/coturn/
- /home/coturn/keys:/data/keys/
- /home/coturn/log:/data/log/
data/turnserver.confas provided- define
your-domain.com static-auth-secretcan be any string. I’d recommend selecting a fully randomized hash with a length of at least 32 to ensure security. OpenSSL can be used to create a random value:openssl rand -hex 64oropenssl rand -base64 64
- define the external-IP to point to your public IP if the server is behind NAT
listening-port,tls-listening-portandmin|max-portmust be opened on outwards facing firewall
- define
#/home/coturn/data/turnserver.conf listening-port=3478 tls-listening-port=5349 external-ip=<public-ip>[/<private-ip>] #defines a mapping between public and private IPs min-port=49100 max-port=49200 fingerprint use-auth-secret static-auth-secret=<create-your-own> realm=<your-domain.com> user-quota=12 total-quota=1200 max-bps=4096000 no-tcp-relay stale-nonce=600 cert=/data/keys/server.crt pkey=/data/keys/server.key CA-file=/data/keys/ca.crt cipher-list="ECDH+AESGCM:DH+AESGCM:ECDH+AES256:DH+AES256:ECDH+AES128:DH+AES:ECDH+3DES:DH+3DES:RSA+AES:RSA+3DES:!ADH:!AECDH:!MD5" no-tlsv1 no-tlsv1_1 no-sslv3 log-file=/data/log/turn.log no-multicast-peers #user=username;password
- To test the server, you can use https://webrtc.github.io/samples/src/content/peerconnection/trickle-ice/ with
turn:<your-domain.com>:<listening_port>using user information which can be defined as hardcoded values inturnserver.conf(user=username;password)please comment the hardcoded user after the test and restart the server - A complete
turnserver.confcan be found at https://github.com/coturn/coturn/blob/master/examples/etc/turnserver.conf
Matrix-Synapse
Configuring Home-Server
Based on the documentation provided in https://github.com/matrix-org/synapse/blob/master/docker/README.md, it’s a relatively straight-forward job to install the docker container.
- Installation path:
/home/synapse- the
/home/synapse/datafolder must be writable by the container. Usually the991:991user:group combination needs to have write-permissions. If this is not guaranteed, the creation ofhomeserver.db(the database created by the internalsqlitedb) will fail and matrix fails to start properly.
- the
- The first step is to create a new sample
homeserver.yamlfile using following command.<your-domain.com>is the domain name of your matrix server, and also will be the suffix for your users (@username:<your-domain.com>).
docker run -it --rm -v/home/synapse/data:/data \
-e SYNAPSE_SERVER_NAME=<your-domain.com> \
-e SYNAPSE_REPORT_STATS=yes \
matrixdotorg/synapse:latest generate
- Following changes are necessary in order to configure the
homeserver.openidresource is used bydimensionintegration server. It should be added to thelisteners.resources.names.- Provided config causes the server to listen for
httpconnections on port8008. public_baseurlMUST not be the same as yourserver_name, but it would make things easier, as thesynapseserver provides a minimum/.well-known/matrixpath.turn_uris(their URL and port) andturn_shared_secretmust be set according to the configuration of the turn-server.- It’s possible to configure an email server for synapse, in order to allow it to send emails on registrations or other events.
client_base_urlcan point to theriotweb-client.
#/home/synapse/data/homeserver.yaml
server_name: "<your-domain.com>"
pid_file: /data/homeserver.pid
public_baseurl: https://<your-domain.com>/
listeners:
- port: 8008
tls: false
type: http
x_forwarded: true
resources:
- names: [client, federation,openid]
compress: false
turn_uris: ["turns:<your-turnserver.com>:5349?transport=udp", "turns:<your-turnserver.com>:5349?transport=tcp", "turn:<your-turnserver.com>:3478?transport=udp", "turn:<your-turnserver.com>:3478?transport=tcp"]
turn_shared_secret: "<your-static-auth-secret-from-turnserver>"
email:
smtp_host: <your-mail-server.com>
smtp_port: <smtp-port>
smtp_user: "<smtp-user>"
smtp_pass: "<smtp-pass>"
# require_transport_security: true
notif_from: "Your Server's Name <your-address@your-domain.com>"
app_name: "Your Application Name"
enable_notifs: false
client_base_url: "<your-riot-url>"
validation_token_lifetime: 15m
- docker-compose can be as followed:
services:
synapse:
image: matrixdotorg/synapse:latest
restart: unless-stopped
container_name: matrix-synapse
environment:
- SYNAPSE_CONFIG_PATH=/data/homeserver.yaml
volumes:
# You may either store all the files in a local folder
- /home/synapse/data:/data
# .. or you may split this between different storage points
# - ./files:/data
# - /path/to/ssd:/data/uploads
# - /path/to/large_hdd:/data/media
ports:
- 8008:8008/tcp
#depends_on:
# - syanpse-db
Note: It’s possible to use an external database instead of the internal
sqlitedelivered with the image. It’s possible to use external (also docker container) databases. Please check https://github.com/matrix-org/synapse#using-postgresql and https://github.com/matrix-org/synapse/blob/master/docs/postgres.md for more info and an example on how to use PostgreSQL.
Configuring Synapse Reverse Proxy
Next step is to configure the reverse proxy for synapse server. for detailed info, please visit https://github.com/matrix-org/synapse#using-a-reverse-proxy-with-synapse.
In this guide, the federation port will be the same as the client connection port. Therefore, it’s not necessary to configure the port 8448. In addition to the /_matrix path, there is a reverse-proxy configured for /_synapse which can be used by synapse-admin or other tools to manage the users and other properties of synapse.
- Don’t forget to replace
<synapse-internal-ip>with the IP address of the docker-machine. - This config assumes that the
httplistener is running on port8008of thesynapseserver. - It also ensures that the
_matrixand_synapseresources are not cached by browsers. - The first
VirtualHostis there to redirect allhttprequests tohttps.
<VirtualHost *:80>
ServerName <your-domain.com>
<IfModule rewrite_module>
RewriteEngine on
RewriteRule ^/(.*) https://%{HTTP_HOST}/$1 [NC,R=301,L]
</IfModule>
</VirtualHost>
<VirtualHost *:443>
ServerName <your-domain.com>;
AllowEncodedSlashes NoDecode
ProxyPass /_matrix http://<synapse-internal-ip>:8008/_matrix nocanon
ProxyPassReverse /_matrix http://<synapse-internal-ip>:8008/_matrix
ProxyPass /_synapse http://<synapse-internal-ip>:8008/_synapse nocanon
ProxyPassReverse /_synapse http://<synapse-internal-ip>:8008/_synapse
<LocationMatch "^/(_matrix|_synapse)">
<IfModule mod_headers.c>
Header set Cache-Control "max-age=0, no-cache, no-store, must-revalidate"
Header set Pragma "no-cache"
</IfModule>
</LocationMatch>
SSLEngine On
SSLCertificateFile "</path/to/server.crt>"
SSLCertificateKeyFile "</path/to/server.key>"
SSLCertificateChainFile "</path/to/ca.crt>"
</VirtualHost>
Creating a new user – Main Admin Account
After configuring the synapse server, it’s necessary to create at least one admin user, in order to be able to use the synapse admin tool. To do so, please use docker exec -it matrix-synapse register_new_matrix_user -c /data/homeserver.yaml https://<server_name> and follow the instructions. Type ‘yes’ if you want to create an admin user. Please note:
matrix-synapseis the name assigned to thesynapseserver usingcontainer_namein respectivedocker-compose.yml. The name might vary if you have not used that config.<server_name>should be the same as in yourhomeserver.yaml./data/homeserver.yamlmight need to be adjusted according to your configurations.
for more information, please visit https://github.com/matrix-org/synapse/blob/master/INSTALL.md#registering-a-user.
Providing .well-known Service Discovery
Synapse server automatically provides minimal discovery data via /.well-known/matrix/client file. But this might not be enough depending on the needs.
One way to provide this information is to manually create and manage JSON files under /.well-known/matrix/{client|server} files.
To do so:
- create the path
/.well-known/matrixon web-server - create the
.htaccessfile and make sure the web-server is set to consider it..htaccessis needed to ensure properCORSheaders onclientandserverfiles, without which the web-clients and other servers won’t be able to use the discovery information.- following headers can be set in
.htaccess
#/.well-known/matrix/.htaccess Header set Access-Control-Allow-Origin "*" Header set Access-Control-Allow-Methods "GET, POST, PUT, DELETE, OPTIONS" Header set Access-Control-Allow-Headers "Origin, X-Requested-With, Content-Type, Accept, Authorization"
- create
/.well-known/matrix/clientwith the following contents. this defines where the clients should look for client-server communication withsynapseserver.
{
"m.homeserver": {
"base_url": "https://<server_name>"
}
}
- if a local
jitsiserver is to be used by clients while trying to create conference calls, please add following config to theclientfile as a new JSON property. Please remember, that the<your-jitsi-domain>doesn’t need thehttps://prefix.
"im.vector.riot.jitsi":{
"preferredDomain": "<your-jitsi-domain>"
}
- Create
/.well-known/matrix/serverwith following contents. this defines the federation information for other servers. if this is not defined, other servers use port8448per default to get information when federating, which has not been enabled by the configuration provided here. It’s also only needed to some extent, as thesynapseserver is already behind ourhttpsenabled reverse-proxy.
{
"m.server": "<server_name>:443"
}
More information on
.well-knownserver discovery can be found in https://matrix.org/docs/spec/client_server/latest#well-known-uri.More Information on necessary
CORSheaders formatrixcan be found in https://matrix.org/docs/spec/client_server/latest#cors.More information on federation delegation and server-server connections can be found in https://github.com/matrix-org/synapse/blob/master/docs/delegate.md.
Installing Synapse-Admin
In order to ease matrix user management, I’d recommend using awesometechnologies/synapse-admin. It’s really easy to install and use.
Note 1: Please do not deactivate users. It’s not possible to reactivate them.
Note 2: Please be careful when exposing this sub-system to the internet. if your admin password is leaked or cracked, then your matrix server can be compromised.
{installation_path}:/home/synapse-admin- Ports: 8001 for
httprequests synapse-admincan be found in https://github.com/Awesome-Technologies/synapse-admin.
#/home/synapse-admin/docker-compose.yml
version: '3'
services:
synapse-admin:
image: awesometechnologies/synapse-admin
container_name: synapse-admin
ports:
- 8001:80
Dimension Integration Server
Installation
Integration servers provide extra services to matrix users. You can read more about integration server for example in https://github.com/turt2live/matrix-dimension.
At the moment, only
riotweb and desktop can use the services fromdimensionintegration server.
The instructions on the website are pretty good, but a summary here:
- Installation path:
/home/dimension- The
/home/dimension/datafolder should be writable from the docker. if the container cannot start, please check the logs to see if the/data/bot.jsonfile is writable; that might be the cause behind the issue.
- The
- Ports:
8184forhttprequests from clients - Before starting the container, create the
config.yamlfile.- Create a user for dimension on matrix server. Its token is needed for configuration of
dimension. To obtain the token, login with the user using riot-desktop client, click on the user, go toSettings > Help & Aboutand scroll to theAdvancedsection. TheAccess Tokencan be found there. The token must be provided inaccessTokenas<dimension-user-token>. homeserver.nameis the your matrix’server_name.homeserver.clientServerUrlis the same as defined in.well-knownservice discovery’shomeserver.base_url.dimension.baseUrl(<your-dimension-domain.com>) is the (sub-)domain, on which yourdimensionserver is accessible. something likedimension.<your-domain.com>…adminsis a list of users with administrative rights inmatrix-synapsewho are allowed to configure and add integration services.webparameters can be left as they are, as there will be a reverse proxy entry for this server’s access over the internet.
- Create a user for dimension on matrix server. Its token is needed for configuration of
#/home/dimension/docker-compose.yml
version: "3"
services:
dimension:
container_name: 'dimension'
image: turt2live/matrix-dimension
ports:
- 8184:8184
volumes:
- /home/dimension/data/:/data/
#/home/dimension/data/config.yaml
web:
port: 8184
address: '0.0.0.0'
homeserver:
name: "<your-domain.com>"
clientServerUrl: "https://<your-domain.com>"
accessToken: "<dimension-user-token>"
admins:
- "<matrix-admin-user>"
widgetBlacklist:
- 10.0.0.0/8
- 172.16.0.0/12
- 192.168.0.0/16
- 127.0.0.0/8
database:
file: "/data/dimension.db"
botData: "/data/bot.json"
goneb:
avatars:
giphy: "mxc://t2bot.io/c5eaab3ef0133c1a61d3c849026deb27"
imgur: "mxc://t2bot.io/6749eaf2b302bb2188ae931b2eeb1513"
github: "mxc://t2bot.io/905b64b3cd8e2347f91a60c5eb0832e1"
wikipedia: "mxc://t2bot.io/7edfb54e9ad9e13fec0df22636feedf1"
travisci: "mxc://t2bot.io/7f4703126906fab8bb27df34a17707a8"
rss: "mxc://t2bot.io/aace4fcbd045f30afc1b4e5f0928f2f3"
google: "mxc://t2bot.io/636ad10742b66c4729bf89881a505142"
guggy: "mxc://t2bot.io/e7ef0ed0ba651aaf907655704f9a7526"
echo: "mxc://t2bot.io/3407ff2db96b4e954fcbf2c6c0415a13"
circleci: "mxc://t2bot.io/cf7d875845a82a6b21f5f66de78f6bee"
jira: "mxc://t2bot.io/f4a38ebcc4280ba5b950163ca3e7c329"
stickers:
enabled: true
stickerBot: "@stickers:t2bot.io"
managerUrl: "https://stickers.t2bot.io"
dimension:
publicUrl: "https://<your-dimension-domain.com>"
logging:
file: /data/logs/dimension.log
console: true
consoleLevel: info
fileLevel: verbose
rotate:
size: 52428800 # bytes, default is 50mb
count: 5
Reverse proxy for dimension
- define following
virtual-hostin APACHE.- The
<dimension-internal-ip>is the IP address of the Docker server, on which the dimension server is installed. - Port
8148is the same as inconfig.yamlmention in the installation guide above. <your-dimension-domain.com>is also defined in the last step.
- The
- After restarting APACHE, check the configuration by visiting
https://<your-dimension-domain.com>. There should be a page defining how to configureriot web-ui. - The first
VirtualHostensures that all traffic goes overHTTPS.
<VirtualHost *:80>
ServerName <your-dimension-domain.com>
<IfModule rewrite_module>
RewriteEngine on
RewriteRule ^/(.*) https://%{HTTP_HOST}/$1 [NC,R=301,L]
</IfModule>
</VirtualHost>
<VirtualHost *:443>
SSLEngine on
ServerName <your-dimension-domain.com>;
ProxyPass / http://<dimension-internal-ip>:8148/
ProxyPassReverse / http://<dimension-internal-ip>:8148/
ProxyRequests On
SSLEngine On
SSLCertificateFile "</path/to/server.crt>"
SSLCertificateKeyFile "</path/to/server.key>"
SSLCertificateChainFile "</path/to/ca.crt>"
</VirtualHost>
Riot Web Client
Installation
The https://riot.im/app/ web-application can work with a self-hosted server as long as the server is available over the internet. but it’s not that “nice” to provide that link to customers or even friends as it might cause some confusion when trying to configure the home-server and other features.
It’s possible to use a self-hosted version of riot web-ui to customize the feeling. This can be done using following guide or by reading the configuration reference in https://github.com/vector-im/riot-web/blob/develop/docs/config.md:
- Installation path:
/home/riot/ - Ports:
8080forhttpconnections - Mapping
/app/themes/<your-theme>is not necessary, but if you want to customize the experience, like adding your own logo and background, it’s easier to manage this folder. For more information on customization, please check the config-reference, the part withbranding. - Either create an empty
/home/riot/data/config.jsonor copy the example from https://riot.im/develop/config.json and start modifying/adding the configurations you want.- a minimal/ optimal example can be found here below.
#/home/riot/docker-compose.yml
version: '3'
services:
riot-ui:
image: vectorim/riot-web
container_name: riot-ui
restart: unless-stopped
volumes:
- /home/riot/data/config.json:/app/config.json
- /home/riot/data/themes/<your-theme>/:/app/themes/<your-theme>
ports:
- 8080:80
- A complete list of configuration and their functionality can be found in the configuration reference mentioned above. My minimal
config.jsonis as follows.- if you don’t have your own
jitsiserver, you can omit thejitsiconfig part. In that case,riotusesjitsi.riot.imwhen creating conference rooms. - you need to define
<your-riot-domain.com>, which is going to be used below when creating the reverse-proxy. - if you want to have your permalinks and share links to be served from your own domain, please set
permalinkPrefixto<your-riot-domain.com>, otherwise you can use the default value (which points to matrix.to) by omitting the option.
- if you don’t have your own
{
"default_server_name": "<your-domain.com>",
"piwik":false,
"brand": "<your riot's name - appearing in title bar>",
"disable_guests":true,
"default_federate": false,
"disable_custom_urls":true,
"branding":{
"authHeaderLogoUrl":"/themes/<your-theme>/<your-logo>",
"welcomeBackgroundUrl":[
"/themes/<your-theme>/<your 1st bg>",
"/themes/<your-theme>/<your 2nd bg>",
...
]
},
"integrations_ui_url": "https://<your-dimension-domain.com>/riot",
"integrations_rest_url": "https://<your-dimension-domain.com>/api/v1/scalar",
"integrations_widgets_urls": [
"https://<your-dimension-domain.com>/widgets"
],
"integrations_jitsi_widget_url":"https://<your-dimension-domain.com>/widgets/jitsi",
"hosting_signup_link": "",
"bug_report_endpoint_url": "https://riot.im/bugreports/submit",
"features": {
"feature_pinning": "labs",
"feature_custom_status": "labs",
"feature_custom_tags": "labs",
"feature_state_counters": "labs",
"feature_many_integration_managers": "labs",
"feature_mjolnir": "labs",
"feature_dm_verification": "labs",
"feature_cross_signing": "enable",
"feature_invite_only_padlocks": "enable",
"feature_event_indexing": "disable",
"feature_bridge_state": "labs",
"feature_presence_in_room_list": "labs",
"feature_custom_themes": "labs"
},
"roomDirectory": {
"servers": [
"<your-domain.com>"
]
},
"enable_presence_by_hs_url": {
"https://<your-domain.com>": true
},
"jitsi":{
"prefferedDomain":"<your-jitsi-domain.com-without-https>"
},
"permalinkPrefix":"https://<your-riot-domain.com>",
"terms_and_conditions_links": [
{
"url": "https://riot.im/privacy",
"text": "Privacy Policy"
},
{
"url": "https://matrix.org/legal/riot-im-cookie-policy",
"text": "Cookie Policy"
}
]
}
Reverse Proxy
- as always, I’ll assume the port on which
riotruns is the same as in provided configuration (i.e.8080) <riot-internal-ip>should be the IP address of the docker machine.riotwill be accessible on<your-riot-domain.com>/- Again, the first
VirtualHostis there to redirect all your traffic overhttps.
<VirtualHost *:80>
ServerName <your-riot-domain.com>
<IfModule rewrite_module>
RewriteEngine on
RewriteRule ^/(.*) https://%{HTTP_HOST}/$1 [NC,R=301,L]
</IfModule>
</VirtualHost>
<VirtualHost *:443>
ServerName <your-riot-domain.com>
ProxyPass / http://<riot-internal-ip>:8080/
ProxyPassReverse / http://<riot-internal-ip>:8080/
ProxyRequests On
SSLEngine On
SSLCertificateFile "</path/to/server.crt>"
SSLCertificateKeyFile "</path/to/server.key>"
SSLCertificateChainFile "</path/to/ca.crt>"
</VirtualHost>
Jitsi Conferencing tool
Installation
Jitsi installation follows the instructions on the DevOPs Guide (Docker) from Jitsi Meet Handbook found at https://jitsi.github.io/handbook/docs/devops-guide/devops-guide-docker. The ports and configuration paths can be changed as needed (as done in my instance).
Note 1: At the moment, it’s not possible to somehow protect the rooms created by
riot. The rooms made by riot will not be password protected and asriotcannot useprosody‘s user list, it’s not possible to protectjitsirooms per default, which means anyone who knows there is a jitsi server on your machine, can connect to it and use is as a conferencing tool.Note 2: Please make sure port
10000/udp(the same port as inJVB_PORTin.env) is also open, otherwise, your calls will drop constantly.
Installation Path:/home/jitsi- create the installation path, go it and clone
jitsi/docker-jitsi-meetinto it using:git clone https://github.com/jitsi/docker-jitsi-meet .. Please note, that the.in the command is mandatory to force cloning into the current directory, which it’s supposed be/home/jitsi. - copy
env.exampleto.env. - use
./gen-passwords.shto automatically create randomized password strings for the.envfile. - create
configdirectories{web/letsencrypt,transcripts,prosody/config,prosody/prosody-plugins-custom,jicofo,jvb,jigasi,jibri}underjitsi-meet-cfg. - go through
.envparameters and check their validity or configure as needed. A list of availableconfigurations can be found in the link posted above, but here an overview of the “important” ones:CONFIGis the path to your local configuration paths (defined in last step underjitsi-meet-cfg).TZis your timezoneHTTP_PORTandHTTPS_PORTare the ports which are to be exposed respectively forhttpandhttpsconnections on docker.PUBLIC_URLis where your jitsi UI is located. something likehttps://<your-jitsi-domain.com>…- you can enable
let's encryptif you want to forward requests directly to jitsi, or you can use the reverse proxy and define your certificates on that – as with the previous dockers. JVB_PORTis the Jitsi-VideoBridge port, mentioned above, which needs to be accessible from the outside world, otherwise, the video connections will drop constantly.
- there is no need to change
docker-compose.yml, as it uses the.envvariables.
Reverse Proxy
<VirtualHost *:443> ServerName <your-jitsi-domain.com> ProxyPass / https://<jitsi-internal-ip>:8043/ ProxyPassReverse / https://<jitsi-internal-ip>:8043/ ProxyRequests On SSLProxyEngine on SSLProxyVerify none SSLProxyCheckPeerCN Off SSLProxyCheckPeerName Off SSLProxyCheckPeerExpire Off SSLEngine On SSLCertificateFile "</path/to/server.crt>" SSLCertificateKeyFile "</path/to/server.key>" SSLCertificateChainFile "</path/to/ca.crt>" </VirtualHost>
Comments are closed, but trackbacks and pingbacks are open.