Matrix è un sistema di comunicazione in tempo reale che offre servizi di chat, chiamata e videochiamata in modo simile ai famosi WhatsApp, Telegram o Signal, ma a differenza di questi è totalmente decentralizzato (cioè privo di una autorità centrale) e distribuito (si appoggia su molti server che funzionano in federazione). Il sistema funziona grazie a numerosi homeserver che ognuno può installare per partecipare al funzionamento del network. Il ruolo di un server Matrix è quello di memorizzare le chat personali di un utente e le informazioni dell'account in un modo molto simile a quello di un server di posta IMAP/SMTP. In questa pagina vediamo come installare un server per la messaggistica Matrix su una Debian GNU/Linux 10 Buster.
Il server di riferimento sviluppato da Matrix per la propria piattaforma è Matrix Synapse. Si tratta di una implementazione adeguata ad eseguire un home server. Queste sono le caratteristiche della nostra installazione:
Cosa occorre:
In Debian esiste il pacchetto matrix-synapse versione 1.24.0, ma è nella suite buster-backports, quindi è necessario aggiungere tale repository in /etc/apt/sources.list:
deb http://deb.debian.org/debian buster-backports main contrib non-free deb-src http://deb.debian.org/debian buster-backports main contrib non-free
Durante l'installazione del pacchetto viene chiesto il nome che avrà il server Matrix, nel nostro caso indicheremo matrix.example.org. È importante scegliere bene il nome in questa fase, infatti se dovessimo cambiare idea sarà necessario reinstallare il server da capo perché molti ID dipendono da quel nome e per il momento non esistono strumenti di migrazione.
Al termine dell'installazione il server dovrebbe essere in ascolto sulla porta 8008/TCP utilizzando il protocollo in chiaro HTTP e sulla porta 8448/TCP con il protocollo cifrato HTTPS. Per impostazione predefinita le porte sono collegate solo su localhost. Nel nostro caso l'avvio del programma falliva perché i certificati SSL/TLS non erano presenti.
Queste le porte generalmente utilizzate da Matrix:
8008/TCP | Protocollo in chiaro HTTP. |
---|---|
8448/TCP | Protocollo cifrato HTTPS. Nel nostro caso abbiamo disabilitato questa porta, sarà il server web Apache a ricevere le richieste HTTPS e inoltrarle in HTTP sulla 8008 via Reverse Proxy. |
La configurazione del programma sta in un file di configurazione e in un database (predefinito SQLite):
Informazioni di debug si trovano nel syslog di sistema e nel log specifico.
Per i nostri scopi (vedere avanti) vogliamo che il server stia in ascolto in HTTP (senza crittografia) solo sulla porta 8008/TCP e che risponda solo sull'indirizzo localhost 127.0.0.1. Le impostazioni relative di homeserver.yaml sono:
no_tls: True listeners: bind_addresses: - '::1' - '127.0.0.1'
Il file yaml contiene informazioni sensibili (ad esempio la password per la creazione di utenti o per accedere al server SMTP), pertanto è opportuno proteggerlo con mode 640 e proprietario matrix-synapse. Quando si modifica il file di configurazione è necessario riavviare il servizio con:
systemctl start matrix-synapse.service
L'impostazione predefinita Debian di matrix-synapse contiene
enable_registration: false
Ciò significa che ogni utente di questo nodo Matrix dovrà essere creato dall'amministratore. In alternativa è possibile avere l'auto-registrazione, come viene offerta ad esempio dal nodo di riferimento matrix.org.
L'utilizzo di TLS è requisito imprescindibile per garantire la sicurezza del server poiché protegge lo scambio dei messaggi che comprendono anche l'invio delle password. Nella configurazione qui presentata il software matrix-synapse non utilizzerà direttamente TLS, ma sarà Apache ad utilizzarlo, passando le richieste a Matrix Synapse sull'indirizzo 127.0.0.1:8008. Il localhost viene considerato sicuro e quindi è accettabile dialogarci in chiaro.
Con Debian 10 Buster è sufficiente installare il pacchetto certbot ed eseguire il comando:
certbot certonly --text --webroot -w /var/www/html -d matrix.example.org
La procedura prevede di creare dei file in /var/www/html/.well-known/ e chiedere a Let's Encrypt di verificarli via http. Al termine dell'operazione i file da utilizzare sono:
Abbiamo preferito utilizzare il server web Apache per la sua versatilità, in rete tuttavia si trovano molte ricette per utilizzare il più compatto Nginx. Dopo aver installato il pacchetto apache2 è necessario attivare i moduli ssl e proxy_http:
apt-get install apache2 a2enmod ssl a2enmod proxy_http systemctl restart apache2
Apache starà in ascolto sulla porta standard HTTP effettuando il redirect automatico su HTTPS; verranno servite anche le richieste HTTPS sulla porta 8448/TCP. In ogni caso tutte le richieste saranno passate con ProxyPass a matrix-synapse verso l'URL http//127.0.0.1:8008.
Dopo aver aggiunto la direttiva Listen 8448 al file /etc/apache2/ports.conf, si effettua la configurazione di Apache nel file /etc/apache2/sites-available/matrix.example.org.conf:
<VirtualHost *:80> ServerName matrix.example.org SSLEngine off DocumentRoot /var/www/html ServerAdmin webmaster@example.org ErrorLog ${APACHE_LOG_DIR}/matrix.example.org/error.log CustomLog ${APACHE_LOG_DIR}/matrix.example.org/access.log combined # Redirect everything to https, except /.well-known/ directory. RedirectMatch permanent ^/((?!\.well-known).*)$ https://matrix.example.org/$1 </VirtualHost> <VirtualHost *:443 *:8448> ServerName matrix.example.org SSLEngine on SSLCertificateFile /etc/letsencrypt/live/matrix.example.org/fullchain.pem SSLCertificateKeyFile /etc/letsencrypt/live/matrix.example.org/privkey.pem ServerAdmin webmaster@example.org DocumentRoot /var/www/html ErrorLog ${APACHE_LOG_DIR}/matrix.example.org/error.log CustomLog ${APACHE_LOG_DIR}/matrix.example.org/access.log combined # HTTP Matrix Synapse ProxyPass / http://127.0.0.1:8008/ nocanon ProxyPassReverse / http://127.0.0.1:8008/ </VirtualHost>
L'eccezione al Redirect per la .well-known directory serve a far funzionare il rinnovo automatico dei certificati Let's Encrypt. La direttiva nocanon è indispensabile, senza di essa abbiamo riscontrato il seguente errore quando si è cercato di accettare la richiesta di messaggio diretto da parte di un utente registrato su matrix.org:
SynapseError: 401 - Invalid signature for server matrix.org with key ed25519:a_RXGa: Unable to verify signature for matrix.org: <class 'nacl.exceptions.BadSignatureError'> Signature was forged or corrupt
Con la configurazione vista sopra, chiamando l'URL http://matrix.example.org/, si viene rediretti prima verso il protocollo HTTPS e quindi al percorso https://matrix.example.org/_matrix/static/. A questo URL c'è semplicemente un messaggio che avvisa dell'homeserver Synapse in esecuzione e invita ad installare un client.
Se si volesse fare a meno del server web, si dovrebbe porre matrix-synapse in ascolto anche in HTTPS sulla porta 8448/TCP. I certificati SSL/TLS saranno ovviamente indicati nel file di configurazione /etc/matrix-synapse/homeserver.yaml:
# WARNING: Don't use TLS in matrix-synapse if port 8448 is used by the HTTP Reverse Proxy. tls_certificate_path: "/etc/matrix-synapse/homeserver.tls.crt" tls_private_key_path: "/etc/matrix-synapse/homeserver.tls.key" tls_dh_params_path: "/etc/matrix-synapse/homeserver.tls.dh" no_tls: False
I file homeserver.tls.crt e homeserver.tls.key sono quelli ottenuti da Let's Encrypt (rispettivamente fullchain.pem e privkey.pem). Vanno copiati per poter assegnare i permessi giusti: proprietario matrix-synapse e mode 644 e 600 rispettivamente. Ovviamente si deve provvedere a ripetere la copia ogni volta che il certificato viene rinnovato. Invece per generare il file homeserver.tls.dh si esegue:
openssl dhparam -out /etc/matrix-synapse/homeserver.tls.dh 2048
Dopo aver scelto il nome del nostro homeserver è opportuno registrarlo nel DNS sia come record di tipo A che come record di tipo SRV. Dichiarare il record SRV è necessario per far funzionare la federazione tra server Matrix. Supponiamo che la zona DNS sia example.org, queste sono le righe di configurazione per Bind9:
matrix IN A 123.234.34.45 _matrix._tcp IN SRV 0 10 8448 matrix.example.org.
Gli utenti del nostro nodo saranno conosciuti alla federazione con il nome @username:matrix.example.org.
Verificare quale versione del software è in esecuzione sul server:
curl https://matrix.example.org/_matrix/federation/v1/version
Nella app Element si prova a configurare il proprio indirizzo email da Impostazioni ⇒ Generali ⇒ Email e numeri di telefono. Quando si aggiunge una email - se le notifiche email sono disattivate sul server - si ottiene l'errore:
Adding an email to your account is disabled on this server
Queste sono le impostazioni in homeserver.yaml relative all'invio di mail:
email: enable_notifs: true smtp_host: "mail.example.org" smtp_port: 587 smtp_user: "smtp-user" smtp_pass: "MySMTPSecret" require_transport_security: True notif_from: "Your Friendly %(app)s Home Server <noreply@example.org>" app_name: Matrix template_dir: res/templates notif_template_html: notif_mail.html notif_template_text: notif_mail.txt notif_for_new_users: True riot_base_url: "http://matrix.example.org/riot"
Con qusta direttiva si dichiara l'URL pubblico:
public_baseurl: https://matrix.example.org:8448/
Infine si deve copiare la directory dei template:
cp -pr /usr/lib/python3/dist-packages/synapse/res /var/lib/matrix-synapse/
Se ci si dimentica di qualche passaggio si ottengono eventualmente gli errori:
ERROR: Password reset emails are enabled on this homeserver due to a partial 'email' block. However, the following required keys are missing: public_baseurl
oppure:
ERROR: Configured template directory does not exist: /var/lib/matrix-synapse/res/templates
Fatto qusto è possibile registrare il proprio indirizzo email nella app. La procedura prevede i seguenti passaggi:
Avendo disabilitato l'auto-registrazione, si deve creare manualmente il primo account, essendo il primo esistente lo faremo di tipo amministratore. Useremo il comando register_new_matrix_user, che però richiede la seguente opzione nel file di configurazione:
registration_shared_secret: MySecret
Eseguendo il comando successivo sulla stessa macchina, non è necessario digitare tale password; questa verrà letta direttamente dal file yaml:
register_new_matrix_user -c /etc/matrix-synapse/homeserver.yaml http://localhost:8008
New user localpart [root]: niccolo Password: Confirm password: Make admin [no]: yes Sending registration request... Success!
Generare un nuovo hash con il tool hash_password (incluso nel pacchetto Debian matrix-synapse):
hash_password -p MySecret $2b$12$6Q.zARcyW0nnRzmmo8d1H.NblSGbj309lBevr/1kiGmtE0FFJGP0S
Collegarsi al database di backend, individuare l'utente e modificare la tabella:
SELECT name FROM users; SET password_hash='$2b$12$6Q.zARcyW0nnRzmmo8d1H.NblSGbj309lBevr/1kiGmtE0FFJGP0S' WHERE name='@niccolo:matrix.rigacci.org';
Si visita la pagina https://riot.im/app/#/login
Other homeserver | https://matrix.example.org |
---|---|
Username | @username:matrix.host.tld |
Password |
Una sessione avviata in questa pagina web può essere anche verificata (passare da Not trusted a Trusted) utilizzando i normali metodi della verifica da altro dispositivo trusted oppure utilizzando la security key.
In generale, se si effettua la disconnessione dal client web di Element, la sessione viene distrutta. I nostri interlocutori dovrebbero vederla scomparire immediatamente dall'elenco delle sessioni attive dell'utente, visualizzabile in room properties ⇒ 2 people ⇒ [account] ⇒ Security.
Il client più utilizzato per accedere alla messaggistica Matrix è Element, esiste per piattaforma Android e iOS, ma esiste anche in versione desktop per Windows e Mac OS.
La versione Android, essendo un programma libero ed open source, è scaricabile sia dal Google Play che da repository alternativi come F-Droid. Fra le due versioni c'è una sostanziale differenza sia in termini di dimensione (circa 22 Mb per la versione Google Play, 50 Mb per la versione F-Droid), sia in termini di funzionalità; la versione Google Play infatti utilizza i servizi Google per la gestione delle notifiche, ottimizzando il traffico e la gestione della batteria a discapito della libertà: infatti è necessario avere un account Google attivo per utilizzarla.
Un account Matrix è costituito da un login e una password, ma c'è un altro elemento altrettanto importante: le chiavi di cifratura di tutte le chat effettuate. Tali chiavi sono memorizzate nella sessione del client (app Element sullo smartphone, oppure interfaccia web riot.im). Se la sessione viene chiusa o distrutta potremo accedere nuovamente al nostro account con login/password, ma non verranno decifrate tutte le chat passate, a meno che non abbiamo salvato la security key. Tale chiave verrà chiesta quando useremo il client per accedere nuovamente al nostro account.
Cosa succede se si perde la password di un account su Matrix.org:
In una chat di messaggi diretti, quando la crittografia end-to-end è attiva, compare il simbolo di uno scudo nero sopra l'icona dell'interlocutore. Questo garantisce che i messaggi sono cifrati appena escono dal nostro dispositivo e vengono decifrati solo sul dispositivo del nostro interlocutore. Neanche l'amministratore dell'homeserver può leggerne il contenuto. Questo tuttavia non garantisce l'identità dell'interlocutore; se vogliamo avere la certezza che l'interlocutore sia davvero chi dice di essere, dobbiamo scambiarci un codice di conferma su un canale diverso da Matrix.
La via più semplice è lo scambio di un codice QR in presenza fisica. Per farlo è sufficiente che uno dei due interlocutori faccia tap sull'intestazione della chat, scelga il menu 2 persone, il nome dell'interlocutore e quindi Sicurezza ⇒ Verifica. Viene avviata una procedura durante la quale uno dei due smartphone genera a video un codice QR e l'altro avvia la fotocamera per scansionare tale codice. Al termine della procedura l'icona dell'interlocutore avrà il simbolo di uno scudo verde.
Un sistema di directory (elenco) consente di cercare e trovare l'ID Matrix di una persona a partire dall'indirizzo email oppure da un numero di telefono. Al momento Matrix non offre un sistema di Identity Server distribuito simile alla federazione degli homeserver; non è facile delegare la verifica di email o numeri di telefono. Per questo motivo attualmente viene suggerito di attivare in maniera facoltativa l'utilizzo dell'identity server centralizzato https://vector.im. Nella app Element è sufficiente accedere alle Impostazioni ⇒ Generali ⇒ Farsi trovare e inserire l'URL del server. Quindi sarà possibile pubblicare il nostro indirizzo email e associarlo al nostro ID Matrix (vector.im provvede ad inviare una email di verifica). Per effettuare questa operazione il nostro homeserver deve supportare l'invio di email.
In maniera analoga è possibile pubblicare sull'Identity Server anche il nostro numero di telefono, ma anche in questo caso il nostro homeserver deve supportare un meccanismo per la verifica del numero di telefono (ad esempio l'invio di un codice di conferma tramite SMS).
ATTENZIONE: Questa impostazione è del tutto facoltativa: si possono utilizzare tutti i servizi Matrix senza utilizzare un Identity Server.
Oltre alla app Element per Android e iOS, esiste anche un client basato su web, si tratta di Element Web (chiamato in precedenza Riot oppure riot-web), scaricabile dal repository GitHub. È possibile installarlo sul proprio server web oppure utilizzare l'istanza presente su https://app.element.io/.
ATTENZIONE: Effettuare il logout dal client web può essere operazione pericolosa se non si salva la Security Key (chiamata anche recovery key), infatti le chiavi crittografiche vivono nella sessione del browser e vengono perse se si chiude la sessione. Si deve fare una copia della Security Key per poter recuperare tutte le chat passate. Quando si effettua un nuovo login verrà chiesta la Security Key per sbloccare le vecchie chat, in alternativa, se abbiamo un altro client correttamente connesso, sarà possibile autorizzare il nostro accesso dalla sessione sull'altro client.
L'installazione predefinita di matrix-synapse in Debian utilizza un database SQLite3 (file /var/lib/matrix-synapse/homeserver.db). Le note di rilascio per la versione 1.7.0 suggeriscono di migrare a Postgres per motivi di prestazioni, soprattutto se si partecipa alla federazione Matrix. Esistono delle opportune istruzioni per utilizzare Postgres. Le istruzioni qui riportate sono semplificate leggermente diverse per adeguarsi all'ambiente Debian.
Verificate che siano installati i pacchetti Debian:
Cambiare utente in postgres ed eseguire nella shell psql i seguenti comandi SQL:
CREATE USER synapse_user PASSWORD 'MyDbSecret'; CREATE DATABASE synapse ENCODING 'UTF8' LC_COLLATE='C' LC_CTYPE='C' template=template0 OWNER synapse_user;
Nel file di configurazione /etc/matrix-synapse/homeserver.yaml deve esserci il parametro server_name, che invece con l'installazione Debian non c'è (pacchetto matrix-synapse versione 1.24.0-1~bpo10+1). Per eseguire lo script synapse_port_db è indispensabile aggiungerlo:
server_name: "matrix.example.org"
Preparare una nuova versione del file di configurazione /etc/matrix-synapse/homeserver.pg.yaml dove cambia solo la sezione database:
# Database configuration database: name: "psycopg2" args: user: synapse_user password: MyDbSecret database: synapse host: 127.0.0.1 cp_min: 5 cp_max: 10
Spostarsi nella directory /var/lib/matrix-synapse/ ed eseguire i sequenti comandi:
#!/bin/sh -xe cd /var/lib/matrix-synapse systemctl stop matrix-synapse.service synapse_port_db \ --sqlite-database /var/lib/matrix-synapse/homeserver.db \ --postgres-config /etc/matrix-synapse/homeserver.pg.yaml mv /etc/matrix-synapse/homeserver.yaml /etc/matrix-synapse/homeserver.yaml.bak mv /etc/matrix-synapse/homeserver.pg.yaml /etc/matrix-synapse/homeserver.yaml systemctl start matrix-synapse.service
La nostra ricetta semplificata tiene fermo il servizio Matrix per tutto il tempo della migrazione. Con database di una certa dimensione questa operazione potrebbe richiedere diversi minuti; vedere le istruzioni originali per un metodo che esegue la migrazione in due o tre passaggi incrementali.