Rocket.Chat

Rocket.Chat ist eine freie Alternative zu Slack und basiert auf Node.js. Da Node.js „single threaded“ ist, kann Rocket.Chat nicht von mehreren CPU-Cores profitieren. Bei vielen Concurrent Users kann Rocket.Chat daher träger reagieren, ein Core wird dann zu 100% durch Node.js ausgelastet. In dem Fall lässt sich Rocket.Chat in mehreren Instanzen betreiben.

Rocket.Chat legt die Inhalte (Chat-Nachrichten, Raum-Konfigurationen etc.) in einer MongoDB ab.

Links

Bemerkung

  • Benutzer aus Raum entfernen: Die Nachrichten des Benutzers im Channel bleiben erhalten.

  • Benutzer in Rocket.Chat löschen: Alle Nachrichten des Benutzers werden aus allen Channels entfernt. Daher sollten Benutzer nur deaktiviert werden, wenn man auf eine konsistente Chat-History Wert legt.

Update

Ein Update/Upgrade entspricht dem Vorgehen der Neuinstallation:

Shutdown Rocket.Chat
Goto the installation folder: cd /opt/
Remove or move the Rocket.Chat folder.
Follow the installation section

Rocket.Chat konfigurieren

Was ist nach einer Erst-Installation einzurichten?

  • Auf dem Reverse Proxy: vHost erstellen

  • Avatar für den Rocket-Administrator und „rocket.cat“ setzen

  • Standard-Sprache deutsch/englisch setzen, je nach Zielgruppe

  • Auf Wunsch die User-Registrierung abschalten: Administration > Accounts > Registration > „Registration Form: Disabled“ und „Registration Form Secret URL“

  • Mail-Einstellungen vornehmen: Administration > Email > SMTP (meist an localhost, 25)

  • Auf Wunsch PIWIK/Matomo integrieren

  • Benutzer anlegen oder LDAP integrieren. Wichtig: Benutzer auf „Verified“ setzen, damit sie im Falle einer Abwesenheit Notifications per E-Mail erhalten.

  • Die ersten Räume einrichten, Benutzer zuteilen

Betrieb hinter Reverse Proxy

SELinux - nach einer Standard-Installation wird sich der Apache Reverse Proxy nicht auf Port 3000 verbinden können:

type=AVC msg=audit(1508497633.925:12355): avc: denied { name_connect } for pid=31373 comm="httpd" dest=3000 scontext=system_u:system_r:httpd_t:s0 tcontext=system_u:object_r:ntop_port_t:s0 tclass=tcp_socket

Deshalb:

setsebool -P httpd_can_network_connect on

Beispiel für einen Apache vHost, der als Reverse Proxy agiert:

<IfModule mod_ssl.c>
  <VirtualHost *:443>
    ServerName chat.example.com

    ProxyRequests Off
    ProxyVia Off

    <Location />
         Require all granted
    </Location>

    RewriteEngine On
    RewriteCond %{HTTP:Upgrade} =websocket [NC]
    RewriteRule /(.*)           ws://10.80.32.19:3000/$1 [P,L]
    RewriteCond %{HTTP:Upgrade} !=websocket [NC]
    RewriteRule /(.*)           http://10.80.32.19:3000/$1 [P,L]

    ProxyPassReverse / http://10.80.32.19:3000/

    <Proxy *>
        Require all granted
    </Proxy>

    SSLEngine on
    SSLOptions +StrictRequire

    SSLCertificateFile /etc/letsencrypt/live/chat.example.com/cert.pem
    SSLCertificateKeyFile /etc/letsencrypt/live/chat.example.com/privkey.pem
    SSLCertificateChainFile /etc/letsencrypt/live/chat.example.com/chain.pem
  </VirtualHost>
</IfModule>

Siehe auch https://docs.rocket.chat/installation/manual-installation/configuring-ssl-reverse-proxy

Backup und Restore

Backup:

  • /opt sichern

  • Mongo-Dump sichern

Daten-Export

Channels (Rooms) und Groups lassen sich mit https://github.com/frdmn/rocketchat-export-channel-messages als CSV oder JSON exportieren, sofern der Benutzer, den man dafür verwendet, die Zugriffsrechte auf die Ressourcen hat. Der Raum-Name muss bekannt sein, also vorher mit dem API-Call channel.listAll etc. arbeiten.

Posten von Messages per Skript

Dafür gibt es zwei Möglichkeiten:

  1. Man postet unter einem bestimmten Benutzer und legt in der Weboberfläche im Profil unter „My Account > Personal Access Tokens“ ein Token an. Das erhaltene Token und die User ID verwendet man dann beispielsweise mit curl:

    curl --header 'X-Auth-Token: YOUR-ACCESS-TOKEN' \
        --header 'X-User-Id: YOUR-USER-ID' \
        --header 'Content-type:application/json' \
        --data '{ "channel": "CHANNEL-NAME", "text": "Test message" }' \
        https://chat.example.com/api/v1/chat.postMessage
    
  2. Man arbeitet mit Webhooks (bevorzugt). Solch einen Hook erstellt man unter „Administration > Integrations > New Integration“, zum Beispiel für einen Raum oder einen Benutzer. Auf der Admin-Page ist dann auch alles beschrieben, man weiter vorgehen muss.

    curl --request POST \
        --header 'Content-Type: application/json' \
        --data '{ "text": "Test message" }' \
        https://chat.example.com/hooks/T6yRim2606JJjfNSRKLqya0815a9QygBvsepZ9wQT
    

Push-Nachrichten

Oft gefragt: Muss ich meine Instanz bei Rocket.Chat registrieren? Wird eine Push-Nachricht nicht von meinem Server direkt verschickt?

Die Push-Notifcations können nicht direkt vom eigenen Rocket.Chat-Server versendet werden: die App-Stores von Google und Apple verlangen, dass in der kompilierten Mobile App fix hinterlegt ist, von welchem Server Push-Notifications stammen. Das Gateway ist also nicht frei konfigurierbar.

Um trotzdem Push-Notifications zu ermöglichen, hostet Rocket.Chat ein Push-Gateway, welches in den Apps hinterlegt ist. Der eigene Rocket.Chat-Server sendet seine Notifications an das Push-Gateway von Rocket.Chat, welches diese dann an das mobile Endgerät weiterleitet. Stand 2020-11 sind kostenlos maximal 10’000 Push-Nachrichten pro Monat pro möglich. Wer mehr benötigt, löst ein Abo, oder man erhält bei Erreichen des Kontingents bis zum Monatsende keine Notifications mehr. Eine Registrierung ist inzwischen damit Pflicht. Siehe auch https://forums.rocket.chat/t/enforcing-registration-requirement-to-utilize-push-gateway/7545

Das offizielle Push-Gateway ist über https://gateway.rocket.chat auf Port 443 erreichbar. Das Senden einer Push-Nachricht vom Rocket.Chat-Server aus ist so auch über einen Outbound-Proxy-Server möglich.

Alternativ kann man ein eigenes Push-Gateway betreiben - allerdings muss man dann die Mobile Apps selbst kompilieren und in den App-Stores anbieten. Ein eigenes Push-Gateway empfehlen wir daher nicht. Siehe auch https://github.com/RocketChat/Rocket.Chat/issues/8692 und https://forums.rocket.chat/t/your-own-push-notifications-not-using-the-default-gateway/7063/2.

Wer Angst hat, dass die Push-Nachrichten sensitive Daten enthalten, die die Rocket.Chat-Entwickler mitlesen können, sendet seine Notifications einfach ohne Inhalt: „Administration > Settings > Push > Privacy > Show Message in Notification: off“.

API

Die Administration klappt auch per API. Das API findet sich im Source Code unter packages/rocketchat-api/server/v1.

Welche API-Methoden sind verfügbar (die Doku hinkt für gewöhnlich hinterher)?

git clone https://github.com/RocketChat/Rocket.Chat
grep -ir 'API\.v1\.addRoute' Rocket.Chat

Am Anfang steht der Login. Man erhält einen „authToken“ und eine „userId“, die für alle nachfolgenden Requests benötigt werden.

curl \
    --request "POST" \
    --data "user=myuser&password=mypassword" \
    https://$ROCKETURL/api/v1/login | jq

Ergibt:

"authToken": "Ew0ATK83_XmHfHWPuFPPmdUqeg1H6nf8kDtkwyPgD5Y"
"userId": "kebvGEeDA56S8rGJL"

Info über Rocket.Chat auslesen - geht ohne Login:

curl https://$ROCKETURL/api/v1/info

Alle Einstellungen holen:

curl \
    --header "X-User-Id: $userId" \
    --header "X-Auth-Token: $authToken" \
    https://$ROCKETURL/api/v1/settings

Alle User auflisten und als csv exportieren:

curl \
    --header "X-User-Id: $userId" \
    --header "X-Auth-Token: $authToken" \
    https://$ROCKETURL/api/v1/users.list?count=250 | jq -r '.users[] | [.username, .lastLogin] | @csv' > login.csv

Alle User der Gruppe „$role“ deaktivieren, welche in den letzten 365 Tagen inaktiv waren:

curl \
    --header "X-Auth-Token: $authToken" \
    --header "X-User-Id: $userId" \
    --header "Content-type:application/json" \
    --data "{ 'daysIdle': 365, 'role': '$role' }" \
    https://$ROCKETURL/api/v1/users.deactivateIdle

Infos über einen Benutzer auslesen:

curl \
    --header "X-User-Id: $userId" \
    --header "X-Auth-Token: $authToken" \
    --header "Content-type:application/json" \
    https://$ROCKETURL/api/v1/users.info?username=myuser

Alle Channels auflisten (Rooms):

curl \
    --header "X-User-Id: $userId" \
    --header "X-Auth-Token: $authToken" \
    --header "Content-type:application/json" \
    https://$ROCKETURL/api/v1/channels.list

Infos über einen Channel auslesen:

curl \
    --header "X-User-Id: $userId" \
    --header "X-Auth-Token: $authToken" \
    --header "Content-type:application/json" \
    https://$ROCKETURL/api/v1/channels.info?roomName=myroom

Notification-Einstellungen für alle Channels anpassen:

for room_id in $(curl --header "X-User-Id: $userId" --header "X-Auth-Token: $authToken" --header "Content-type:application/json"  https://$ROCKETURL/api/v1/rooms.get | jq '.update[] | select(.t == "p")._id'); do
    curl \
        --request POST \
        --header "X-User-Id: $userId" \
        --header "X-Auth-Token: $authToken" \
        --header "Content-type:application/json" \
        --data-raw "{\"roomId\": $room_id, \"notifications\":{\"disableNotifications\":\"0\", \"muteGroupMentions\":\"0\", \"hideUnreadStatus\":\"0\", \"hideMentionStatus\":\"0\", \"desktopNotifications\":\"default\", \"audioNotificationValue\":\"default\", \"mobilePushNotifications\":\"default\", \"emailNotifications\":\"default\"}}" \
        https://$ROCKETURL/api/v1/rooms.saveNotification
done

Channel löschen:

curl \
    --request POST \
    --header "X-User-Id: $userId" \
    --header "X-Auth-Token: $authToken" \
    --header "Content-type:application/json" \
    --data '{ "roomName": "myroom" }' \
    https://$ROCKETURL/api/v1/channels.delete

Alle Private Groups auflisten:

curl \
    --header "X-User-Id: $userId" \
    --header "X-Auth-Token: $authToken" \
    https://$ROCKETURL/api/v1/groups.listAll

Private Group löschen - das geht nur, wenn der API-User auch Admin-Mitglied der Private Group ist:

curl \
    --request POST \
    --header "X-User-Id: $userId" \
    --header "X-Auth-Token: $authToken" \
    --header "Content-type:application/json" \
    --data '{ "roomName": "myroom" }' \
    https://$ROCKETURL/api/v1/groups.delete

Einen Member aus einem Channel entfernen:

curl \
    --request DELETE \
    --header "X-User-Id: $userId" \
    --header "X-Auth-Token: $authToken" \
    --header "Content-type:application/json" \
    --data '{ "roomName": "myroom", "username": "userName" }' \
    https://$ROCKETURL/api/v1/channels.kick

Migration von Server A nach Server B

Sicherstellen, dass auf Server A und B die gleiche Rocket.Chat-Version installiert ist.

# Host A
systemctl stop rocketchat
mongodump --db rocketchat --out /tmp/mongodump/
tar cvf backup.tar ~/backup
scp backup.tar hostb:...

# Host B
systemctl stop rocketchat
# deprecated synatx
# mongorestore /tmp/mongodump/rocketchat --db rocketchat --drop
mongorestore /tmp/mongodump/rocketchat --nsInclude='rocketchat.*' --drop
systemctl start rocketchat

Achtung! --drop löscht alle Tablellen, die im Dump vorhanden sind, bevor es den Dump einfügt.

Troubleshooting

Den einzigen Admin eines Raumes entfernt?

Schlecht, denn dann lässt sich der Raum auch vom globalen Admin-Account nicht mehr über die Rocket.Chat-Oberfläche administrieren.

Lösung: ausgewählte User per API einem Raum zuordnen, (einen) User zum Admin und Raum-Owner machen, Raum administrieren/löschen, unnötige Benutzer entfernen und zu hoch vergebene Rechte wieder entfernen.

File-Uploads funktionieren nicht?

In /var/log/messages taucht folgendes auf?

rocket-chat: ufs: cannot write chunk of file "YJQb5H6y7YaE9psAM" (ENOENT: no such file or directory, open '/tmp/ufs/YJQb5H6y7YaE9psAM')
rocket-chat: ufs: cannot delete temp file "/tmp/ufs/YJQb5H6y7YaE9psAM" (ENOENT: no such file or directory, unlink '/tmp/ufs/YJQb5H6y7YaE9psAM')
rocket-chat: [Error: FileNotFound: no file with id YJQb5H6y7YaE9psAM found]

Lösung:

mkdir /tmp/ufs
chown rocketchat:rocketchat /tmp/ufs
Login der Smartphone-App funktioniert auch nach Neuinstallation der App nicht?

2FA deaktivieren, Login, 2FA aktivieren

Built on 2023-09-21