docs: add moderation/content-scanning deployment guide (Issue #18)
This commit is contained in:
@@ -0,0 +1,109 @@
|
||||
# Moderation Bot & Content Scanning
|
||||
|
||||
**Status**: ✅ Draupnir deployed (2026-07-29, Closes Issue #18) | ⏳ Content Scanner geplant, noch nicht umgesetzt (Issue #19)
|
||||
**Konfiguration**: `apps/production/draupnir*.yaml`
|
||||
|
||||
## 1. Draupnir (Moderationsbot)
|
||||
|
||||
Community-Nachfolger von Mjolnir. Läuft als eigener Bot-Account (`@draupnir:axion1337.chat`),
|
||||
verwaltet Ban-Listen ("Policy Rooms") und setzt sie in geschützten Räumen durch.
|
||||
|
||||
### Warum Draupnir statt Mjolnir?
|
||||
|
||||
Mjolnir gilt als Vorgänger-Projekt und wird von der Community nicht mehr aktiv weiterentwickelt;
|
||||
Draupnir ist der aktive Fork mit denselben Kernfunktionen plus Erweiterungen (u.a. native
|
||||
Rust-Crypto-Unterstützung, siehe unten).
|
||||
|
||||
### Bot-Account & Zugriff (Bootstrap)
|
||||
|
||||
Da Authentifizierung über MAS läuft (kein klassisches `registration_shared_secret`), wird der
|
||||
Bot-Account über MAS' eigenes CLI-Tool angelegt:
|
||||
|
||||
```bash
|
||||
kubectl exec -it -n matrix deploy/matrix-stack-matrix-authentication-service -- \
|
||||
mas-cli manage register-user draupnir --yes
|
||||
|
||||
kubectl exec -it -n matrix deploy/matrix-stack-matrix-authentication-service -- \
|
||||
mas-cli manage issue-compatibility-token draupnir
|
||||
```
|
||||
|
||||
Der ausgegebene Token wird per `sops apps/production/draupnir-secret.yaml` manuell eingetragen
|
||||
(kein automatisierter Schritt - der Token darf nirgends unverschlüsselt landen).
|
||||
|
||||
### Wichtige Stolpersteine (live gefunden, nicht aus der Doku ableitbar)
|
||||
|
||||
- **Version**: `gnuxie/draupnir:v2.9.0` crasht beim ersten Start mit `initialManager`
|
||||
("Can't join remote room because no servers..."). Das automatische Anlegen des
|
||||
Management-Rooms über `initialManager` funktioniert erst **ab v3.1.0**. Aktuell deployt:
|
||||
`v3.1.0`.
|
||||
- **CLI-Argument statt Env-Var**: v3.x hat die automatische Config-Erkennung über
|
||||
`NODE_CONFIG_DIR` entfernt - der Container braucht jetzt explizit
|
||||
`args: ["bot", "--draupnir-config", "/data/config/default.yaml"]`, sonst
|
||||
`TypeError: No configuration path has been found for Draupnir.` (per Extraktion von
|
||||
`dist/config.js` aus dem Image bestätigt, nicht dokumentiert gefunden).
|
||||
- **NetworkPolicy**: Der Bot muss Synapse direkt anrufen können. Da `matrix-stack-synapse`
|
||||
intern über haproxy geroutet wird und `allow-ingress-haproxy` standardmäßig nur Traefik
|
||||
(`kube-system`) erlaubt, braucht Draupnir eine eigene `podSelector`-Ausnahme in
|
||||
`networkpolicy.yaml` - sonst schlägt jede Anfrage an den Homeserver silent fehl.
|
||||
|
||||
### Verschlüsselter Management-Room
|
||||
|
||||
Standardmäßig unverschlüsselt (Draupnirs zugrundeliegende Bot-Library aktiviert Crypto nicht
|
||||
automatisch). Für einen verschlüsselten Management-Room:
|
||||
|
||||
1. `experimentalRustCrypto: true` in der Config ergänzen (via `sops`) - vom Hersteller selbst
|
||||
als "not considered production safe" gekennzeichnet, in unserem Test aber ohne Fehler
|
||||
gelaufen (Pod stabil, kein Crash, `End-to-end encryption enabled` in den Logs).
|
||||
2. Verschlüsselung ist eine Raum-Eigenschaft, die beim Erstellen gesetzt wird - das Flag allein
|
||||
verschlüsselt einen bereits bestehenden Management-Room **nicht** rückwirkend. Dafür in
|
||||
Element: Raumeinstellungen → Sicherheit & Datenschutz → Verschlüsselung aktivieren.
|
||||
|
||||
### Profilbild setzen
|
||||
|
||||
Erfordert eine `mxc://`-URL (Bild muss zuerst hochgeladen werden, z.B. per Chat an den Bot
|
||||
senden, dann in Element per "View Source" die `mxc://`-URL kopieren):
|
||||
|
||||
```
|
||||
!draupnir avatar mxc://<server>/<media-id>
|
||||
```
|
||||
|
||||
### Befehle (Kurzreferenz)
|
||||
|
||||
Alle Befehle im (verschlüsselten) Management-Room, Präfix `!draupnir`:
|
||||
|
||||
| Befehl | Zweck |
|
||||
|--------|-------|
|
||||
| `status` | Bot-Status, beobachtete Listen, geschützte Räume |
|
||||
| `rooms add <room>` | Raum unter Draupnirs Schutz stellen (Voraussetzung für Bans!) |
|
||||
| `list create <shortcode> <alias>` | Neue Policy-Liste anlegen (wird automatisch beobachtet + geschützt) |
|
||||
| `watch <shortcode>` | Zusätzliche Policy-Liste beobachten |
|
||||
| `ban <user> <liste> <grund>` | **Wichtig**: 2. Argument ist die Policy-Liste, NICHT der Ziel-Raum! Der Ban gilt automatisch in allen Räumen, die diese Liste beobachten und geschützt sind |
|
||||
| `kick <user> <room> <grund>` | Direkter, sofortiger Kick aus einem konkreten Raum (ohne Listen-Umweg) |
|
||||
| `rules` | Zeigt die Regeln einer Policy-Liste an |
|
||||
| `unban <user> <liste>` | Regel wieder entfernen |
|
||||
|
||||
**Live getestet** (2026-07-29): Testraum geschützt, Policy-Liste angelegt, Testnutzer über
|
||||
`ban`+Liste erfolgreich aus dem geschützten Raum entfernt. Kernmechanismus bestätigt
|
||||
funktionsfähig.
|
||||
|
||||
## 2. Content Scanner (Issue #19, LOW - noch nicht umgesetzt)
|
||||
|
||||
**Wichtige Einschränkung, vorab geklärt**: `matrix-content-scanner-python` ist ein Proxy, den
|
||||
der **Client** explizit statt der normalen Media-Endpunkte aufrufen muss - Synapse selbst
|
||||
leitet nichts automatisch dorthin um. Diese client-seitige Unterstützung existiert nur noch in
|
||||
den veralteten, nicht mehr gepflegten Android/iOS-SDKs. Weder aktuelles Element Web
|
||||
(matrix-js-sdk, was hier läuft) noch Element X unterstützen das. Zusätzlich hat Synapse bei
|
||||
verschlüsselten Anhängen ohnehin nie den Schlüssel - nur ein kooperierender Client kann ihn dem
|
||||
Scanner geben.
|
||||
|
||||
**Konsequenz**: Falls umgesetzt, schützt der Scanner **keinen echten Nutzer-Traffic
|
||||
automatisch** - nur manuelle/skriptgesteuerte Admin-Prüfungen sind möglich (z.B.
|
||||
`kubectl port-forward` + `curl` nach manuellem Upload). Eine echte, transparente Absicherung
|
||||
bräuchte entweder einen Client-Fork oder ein eigenes Synapse-`check_media_file_for_spam`-Modul
|
||||
(deutlich größerer, separater Aufwand).
|
||||
|
||||
Geplante Komponenten bei Umsetzung: ClamAV (`clamav/clamav:1.5.3`, eigene PVC für die
|
||||
Signatur-DB) + `vectorim/matrix-content-scanner` (Config-Keys `scan.script`/
|
||||
`scan.temp_directory`/`crypto.request_secret_path` - aus dem echten `config.sample.yaml`
|
||||
bestätigt). Kein Ingress, keine NetworkPolicy-Ausnahme nötig, da nichts im Cluster oder von
|
||||
außen automatisch darauf zugreift.
|
||||
Reference in New Issue
Block a user