Update du 19/05/2019 - Cette procédure fonctionne aussi pour un Raspberry PI3 (armhf)
Ce bot permet l’intégration de nombreuses fonctionnalités, dont Giphy (Gifs animés) et l’extension du système d’alerte de l’application de monitoring Prometheus. Cette instruction peut aussi être appliqués à des plateformes amd64 (PC).
Le projet “go-neb” est hébergé ici https://github.com/matrix-org/go-neb, la documentation explique clairement comment installer le service. Cependant, la compilation ne s’est pas déroulée comme indiqué.
Compilation
J’ai rencontré deux problèmes : le package inclus dans la distribution “mattn/go-sqlite3” est impossible à compiler et indique ce type d’erreur :
github.com/matrix-org/go-neb/api/handlers
sqlite3-binding.c: In function ‘wherePathSolver’:
sqlite3-binding.c:130692:1: internal compiler error: in schedule_block, at haifa-sched.c:6593
}
j’ai donc installé le paquet DEBIAN golang-github-mattn-go-sqlite3-dev en remplacement.
Le second problème est situé au niveau d’un “include” que le builder “go” ne trouve pas (détecté en lançant la commande :
go build /opt/go-neb/vendor/src/github.com/mattn/go-sqlite3/sqlite3.go
et présente l’erreur :
tmp/go-build020128959/command-line-arguments/_obj/sqlite3.cgo2.o: In function `_sqlite3_bind_blob': vendor/src/github.com/mattn/go-sqlite3/sqlite3.go:44: undefined reference to`sqlite3_bind_blob'
/tmp/go-build020128959/command-line-arguments/_obj/sqlite3.cgo2.o: In function `_sqlite3_bind_text': vendor/src/github.com/mattn/go-sqlite3/sqlite3.go:39: undefined reference to`sqlite3_bind_text'
En regardant le code, celui-ci fait mention d’un include
#include <sqlite3-binding.h>
qui fait également appel à l’include :
#include <sqlite3.h>
non présent dans le package, mais disponible au travers du package DEBIAN libsqlite3-dev. Je pense qu’il s’agit simplement d’un problème de paramétrage du chemin de recherche des includes. Par facilité, j’ai choisi de copier le fichier manquant dans le package de distribution.
Préparation
apt install go-lang libsqlite3-dev golang-github-mattn-go-sqlite3-dev git
cd /opt
git clone https://github.com/matrix-org/go-neb
export GOPATH=/usr/lib/go-1.7/
export PATH=$PATH:$GOPATH/bin
go get github.com/constabulary/gb/...
cd go-neb
rm -r vendor/src/github.com/mattn/go-sqlite3
cp -R /usr/share/gocode/src/github.com/mattn/go-sqlite3 vendor/src/github.com/mattn/
cp /usr/include/sqlite3.h ./vendor/src/github.com/mattn/go-sqlite3/
Compilation du projet
gb build github.com/matrix-org/go-neb
Le binaire go-neb a été créé dans le répertoire “bin” du projet.
Répertoire la base de données sqlite3
Créer le répertoire db
mkdir db
Créer un installateur sous forme d’archive (tar.gz)
cd /opt/go-neb
tar cfz /root/go-neb.tgz /opt/go-neb/bin /opt/go-neb/db
Vous pouvez maintenant installer cette archive sur n'importe quel serveur arm64 :
Copier l'archive dans le répertoire** /root/** du serveur
cd /
tar xfz /root/go-neb.tgz
rm /root/go-neb.tgz
Fichier pour le service systemd
Ce service va communiquer avec le service Synapse-Matrix. Pour faire simple, j’ai installé le service sur le serveur qui héberge le service Synapse-Matrix.
Il écoute sur le port : TCP/4050 à l’adresse IP : localhost.
La base de données utilisée par ce service est de type sqlite3 et stockée dans le répertoire /opt/go-neb/db. Ces paramètres sont personnalisables dans le fichier qui suit.
Après mise en place, si vous devez modifier ce fichier, pensez toujours à exécuter la commande :
systemctl daemon-relaod
#Créer le groupe et user d'éxécution
addgroup go-neb
adduser --system --home /opt/go-neb/ --no-create-home --disabled-password --shell /bin/nologin --ingroup go-neb go-neb
#Modification du propriétaire du répertoire d'installation
chown -R go-neb:go-neb /opt/go-neb
#Créer le fichier pour systemd
vi /etc/systemd/system/go-neb.service
et insérer ces instructions :
[Unit]
Description=Go-neb Bot For Synapse-Matrix server
After=network.target
[Service]
WorkingDirectory=/opt/go-neb
ExecStart=/opt/go-neb/bin/go-neb
StandardOutput=syslog
StandardError=syslog
SyslogIdentifier=go-neb
User=go-neb
Group=go-neb
Environment=BIND_ADDRESS=localhost:4050 DATABASE_TYPE=sqlite3 DATABASE_URL=db/go-neb.db?_busy_timeout=5000 BASE_URL=http://localhost:4050
Restart=always
RestartSec=10
StartLimitInterval=900
StartLimitBurst=3
[Install]
WantedBy=multi-user.target
Démarrage du service
systemctl start go-neb
# Vérifiez le lancement
tail -f /var/log/syslog
Exemple de réponse :
Apr 25 10:03:40 localhost systemd[1]: Started Go-neb Bot For Synapse-Matrix server.
Apr 25 10:03:40 localhost go-neb[5662]: time="2019-04-25T10:03:40+05:30" level=info msg="Go-NEB ({BindAddress:localhost:4050 DatabaseType:sqlite3 DatabaseURL:db/go-neb.db?_busy_timeout=5000 BaseURL:http://localhost:4050 LogDir: ConfigFile:})"
Le service est démarré et écoute sur le port 4050 de l’interface localhost :
#Vérification
netstat -ant|grep 4050
Activation du service au boot du serveur
systemctl enable go-neb
Paramétrage du Bot
Le bot doit pouvoir se connecter au serveur Synapse-Matrix. Créer un compte d’accès au service Synapse-Matrix, en adaptant les paramètres à votre configuration :
/opt/synapse/env/bin/register_new_matrix_user -c /opt/synapse/homeserver.yaml http://matrix.mondomaine.com
J’ai utilisé le compte “botgoneb” avec un mot de passe fort, et non admin.
Pour obtenir le token de ce nouvel utilisateur, utilisez la commande suivant en l’adaptant à votre configuration :
curl -X POST "http://matrix.mondomaine.com/_matrix/client/r0/login" -d '{"type":"m.login.password", "user":"botgoneb", "password":"[Mot de passe entré précédemment]"}'
Réponse de la commande si elle aboutit :
{
"access_token": "[TOKEN UTILISATEUR]",
"device_id": "XXXXXX",
"home_server": "matrix.mondomaine.com",
"user_id": "@botgoneb:matrix.mondomaine.com"
}
Le TOKEN de ce nouvel utilisateur est la valeur correspondant à la clé “access_token” de la réponse.
Connectez-vous au serveur Synapse-Matrix et exécutez la commande suivante, elle permet d’indiquer au service “go-neb” la manière de se connecter au service Synapse-Matrix
curl -X POST localhost:4050/admin/configureClient --data-binary '{
"UserID": "@botgoneb:matrix.mondomaine.com",
"HomeserverURL": "http://matrix.mondomaine.com",
"AccessToken": "<TOKEN obtenu précédemment>",
"Sync": true,
"AutoJoinRooms": true,
"DisplayName": "Bot goneb"
}'
La commande s’exécute normalement et renvoi une valeur au format JSON.
J’active pour le test la fonction “echo” du service “go-neb”
curl -X POST localhost:4050/admin/configureService --data-binary '{"Type": "echo","Id": "00001","UserID": "@botgoneb:matrix.mondomaine.com","Config": {} }'
La commande renvoi une valeur au format JSON, la fonction est activée.
Connectez-vous à un client Element, créer un salon et invitez le bot : @botgoneb:matrix.mondomaine.com**, sa réaction est immédiate, il est connecté. Tapez dans ce salon le message :
!echo hello world
Le bot répond en indiquant le texte saisi après la commande “!echo”.
Intégration Giphy - Serveur Synapse-Matrix
Activation de la fonction : Se connecter à la console du serveur disposant du service “go-neb”, et tapez la commande :
curl -X POST localhost:4050/admin/configureService --data-binary '{
"Type": "giphy",
"Id": "00002",
"UserID": "@botgoneb:matrix.mondomaine.com",
"Config": {"api_key":"dc6zaTOxFJmzC"}
}'
Je vous conseille de vous enregistrer chez Giphy (https://developers.giphy.com/) en créant une application (“Create app”). Ceci permet d’obtenir une clé API. La clé indiquée ci-avant est la clé publique Giphy, disposant d’un quota d’utilisation quotidien. Quand le quota est atteint, le serveur Giphy ne renvoit rien.
Inviter le bot dans le salon de votre choix, il se connecte immédiatement, et utilisez tapez le message : !giphy [mot recherché] Exemple : !giphy test
le bot renvoi la première image Gif retournée par Giphy.
Element.io permet de désactiver le démarrage automatique des Gifs, regardez dans les paramètres de votre compte.
Intégration AlertManager/Prometheus monitoring - Serveur Synapse-Matrix
Cette fonction permet au service AlertManager (partie du projet Prometheus - Système de monitoring développé par Soundcloud - installation cliquez-ici ), d’envoyer les alertes au système Synapse-Matrix. Cette partie n’est pas documentée sur le web, après plusieurs heures d’analyses du code source concernant le bot, et d’exécution de tests, cette partie est maintenant fonctionnelle.
Flux de communications Prometheus / Alertmanager / go-neb / Synapse-Matrix / Utilsateur Element.io
Pour séparer les fonctions de chaque bot, je crée un nouvel utilisateur sur Synapse-Matrix :@botPrometheus:matrix.mondomaine.com. Je récupère son token d’accès et l’ajoute au système go-neb (voir ci-avant).
Je crée le salon “Monitoring”, destiné à recevoir les message du bot : “#Monitoring:matrix.mondomaine.com”.
Récupérer l’ID interne de ce salon, en utilisant le client Element.io : Sélectionnez le salon, entrez sur “Setting”, “Advanced”, l’ID interne apparaît sous la forme : !qmElAGdFYCHoCJuaNt:matrix.mondomaine.com
Modification de l’adresse d’écoute du service go-neb
Le paramétrage original du service “go-neb”, indique une écoute à l’adresse “localhost”. Le service “Alertmanager”, situé sur un autre serveur, ne peut par conséquent pas joindre le service “go-neb”. Je vais donc changer la configuration du service “go-neb” afin que celui-ci écoute sur l’interface réseau connectée au réseau local.
vi /etc/systemd/system/go-neb.service
#Modifier la valeur des variables d'environnement : Environment=BIND_ADDRESS=localhost:4050 DATABASE_TYPE=sqlite3 DATABASE_URL=db/go-neb.db?_busy_timeout=5000 BASE_URL=http://localhost:4050
Remplacer “localhost” par l’adresse IP de ce serveur :
Environment=BIND_ADDRESS=192.168.1.12:4050 DATABASE_TYPE=sqlite3 DATABASE_URL=db/go-neb.db?_busy_timeout=5000 BASE_URL=http://192.168.1.12:4050
Enregistrer et quitter vi
Actualisez systemd et redémarrer go-neb :
systemctl daemon-reload
systemctl restart go-neb
Vérifiez avec :
netstat -ant|grep 4050
Ajouter les règles Firewall sur l’interface concernée : INPUT TCP/4050 et filtrer uniquement le serveur disposant du service Alertmanager.
Le service “Alertmanager” peut maintenant joindre le service “go-neb”.
Activation de la fonction alertmanager de go-neb
Cette fonction s’active en utilisant la commande curl suivante :
curl -X POST http://192.168.1.12:4050/admin/configureService --data-binary '{
"Type": "alertmanager",
"Id": "00003",
"UserID": "@botprometheus:matrix.mondomaine.com",
"Config": {"rooms":
{"!qmElAGdFYCHoCJuaNt:matrix.mondomaine.com":
{
"text_template":"Notification Prometheus [{{.Status}}]",
"html_template":"<h1>Notification Prometheus [{{.Status}}]</h1><hr/>{{- range .Alerts}}<div>Alerte : {{.Labels.alertname}}<br/>Instance : {{.Labels.instance}}<br/>Résumé : {{.Annotations.summary}}<br/>Sévérité : {{.Annotations.severity}}<br/>Description : {{.Annotations.description}}<br/>Date/heure de détection : {{.StartsAt}}<br/>{{if ne .EndsAt \"0001-01-01T00:00:00Z\" -}}Date/heure résolution: {{.EndsAt}}<br/>{{- end }}Url : {{.GeneratorUrl}}</div>{{- end}}","msg_type":"m.text"}}}}'
Les paramètres “text_template” et “html_template” sont de type “texte” dont la forme doit respecter la syntaxe concernant les templates “Golang”.
J’ai créé ces templates en me basant sur le code source Javascript utilisé pour l’intégration “Alertmanager” du service de messagerie instantanée “Rocketchat” (Voir l’installation ici).
Le système de templating “Golang” permet de créer des boucles, l’inclusion de conditions, etc, à l’image d’autre systèmes comme “Ejs pour Javascript”, ou “Twig” pour PHP.
Attention, je n’ai pas réussi à insérer le paramètres “style” dans les balises HTML, si quelqu’un souhaite se lancer… Le formatage des données n’est pas supporté ( Ex : .StartsAt | formatAsDate ).
Ce tuto m’a bien aidé : http://goinbigdata.com/example-of-using-templates-in-golang/
Deux templates “go-neb” pour Alermanager/Prometheus sont nécessaires :
- Le template “text_template” est utilisé pour la notification système, le petit popup qui s’affiche quand l’application Element.io reçoit un message.
- Le template “html_template” est utilisé pour construire le corps du message tel que vous le voyez apparaître dans le salon.
Attention le serveur va nous retourner l’adresse du webhook, qui sera utilisée par Alertmanager.
Exemple de données obtenues (format JSON) :
{"ID":"00003","Type":"alertmanager","OldConfig":{},"NewConfig":{"webhook_url":"http://localhost:4050/services/hooks/EDFEERdDM","rooms":....
L’adresse à fournir aux système de webhook de Alertmanager sera dans ce cas précis : http://localhost:4050/services/hooks/EDFEERdD
Modification de la configuration Alertmanager
J’indique à Alertmanager l’adresse du webhook à atteindre (url donnée par l’activation du service “alertmanager” de go-neb. Editer le fichier de configuration Alertmanager (/opt/alertmanager-[version]/alertmanager.yml), en ajoutant dans le bloc “receiver”, le bloc “webhook_config” :
Attention fichier YAML, n’utilisez pas les tabulations mais des espaces, pour indenter les lignes.
[..]
receivers:
- name: 'email'
email_configs:
- send_resolved: true
to:
[..]
webhook_configs:
- send_resolved: true
url: '**http://localhost:4050/services/hooks/EDFEERdDM**'
Recharger la configuration Alertmanager :
systemctl reload prometheus-alertmanager
Tester la notification
Exécuter les commandes qui suivent, en les adaptant à vos paramètres, et à partir du serveur qui héberge le service AlertManager (à cause des règles de Firewall).
Vous recevrez immédiatement un message dans la salon “#Monitoring:matrix.mondomaine.com”.
Test : Détection d’un défaut
curl -X POST http://192.168.1.12:4050/services/hooks/EDFEERdD --data-binary '{
"status": "firing",
"alerts": [{"labels" : {"alertname":"InstanceDown","instance" : "localhost:9100"},
"annotations": {"summary" : "Le service ne répond plus","severity":"Elevé","description":"Le service node_exporter est arrêté ou bien le serveur est éteint"},
"startsAt" : "2019-04-26T06:28:39.456891295+05:30",
"endsAt" : "0001-01-01T00:00:00Z",
"GeneratorUrl" : "http://test"}
]}'
L’heure de résolution n’apparaît pas dans l’alerte
Test : Défaut résolu (dispose d’une date réelle de fin - endsAt)
curl -X POST http://192.168.1.12:4050/services/hooks/EDFEERdD --data-binary '{
"status": "firing",
"alerts": [{"labels" : {"alertname":"InstanceDown","instance" : "localhost:9100"},
"annotations": {"summary" : "Le service ne répond plus","severity":"Elevé","description":"Le service node_exporter est arrêté ou bien le serveur est éteint"},
"startsAt" : "2019-04-26T06:28:39.456891295+05:30",
"endsAt" : "2019-04-26T07:28:39.456891295+05:30",
"GeneratorUrl" : "http://test"}
]}'
L’heure de résolution apparaît dans l’alerte
Enjoy!!!
Compléments pour la production
Si vous démarrer plusieurs services go-neb pour une même instance Matrix, vous constaterez que chaque appel au service Go-neb, sera exécuté autant de fois que vous disposez de service go-neb actif. Si vous souhaitez mettre en place de la haute disponibilité pour ce service, mettez en place un système heartbeat, avec ipfailover.
Licence de ce document : Creative Commons (CC BY-NC-ND 4.0)
CETTE DOCUMENTATION EST LIVRÉE “EN L’ÉTAT”, SANS GARANTIE D’AUCUNE SORTE ET DISTRIBUÉE DANS UN BUT ÉDUCATIF EXCLUSIVEMENT. L’AUTEUR, CONTRIBUTEURS DE CETTE DOCUMENTATION OU ©MYTINYDC.COM NE SAURAIENT EN AUCUN CAS ÊTRE TENUS RESPONSABLES DES DOMMAGES DIRECTS OU INDIRECTS POUVANT RÉSULTER DE L’APPLICATION DES PROCÉDURES MISES EN ŒUVRE DANS CETTE DOCUMENTATION, OU DE LA MAUVAISE INTERPRÉTATION DE CE DOCUMENT.
Commentaires (non traduits)
Pas de commentaires
Poster un commentaire