Ansible Playbooks verwalten mit semaphore

Datum

semaphore bezeichnet sich selbst einfach nur als „open source Ansible UI“ und erfüllt als diese auch ihren Zweck.

Installation

Voraussetzung für die Installation von semaphore ist eine MySQL-Instanz.
Ein MySQL oder Mariadb ab der Version 5.5 reicht da schon aus.

Ich verwende bei mir folgendes:

Name       : mariadb-server
Architektur : x86_64
Version    : 5.5.60
OS: CentOS Linux release 7.6.1810 
Ansible Version: ansible-playbook 2.7.8

Github-Seite des Projekts: https://github.com/ansible-semaphore

Ich installiere das auf der Github-Projektseite bereitgestlellte Release per rpm:

$ wget https://github.com/ansible-semaphore/semaphore/releases/download/v2.5.1/semaphore_2.5.1_linux_amd64.rpm
$ rpm -i semaphore_2.5.1_linux_amd64.rpm

Einrichten von semaphore

Das Setup beginnt, wenn semaphore mit dem Parameter -setup gestartet wird.

Hier gitl es nun noch ein paar Standardwerte zu setzen:

$ semaphore -setup                                                                                                                                                                               

 Hello! You will now be guided through a setup to:

 1. Set up configuration for a MySQL/MariaDB database
 2. Set up a path for your playbooks (auto-created)
 3. Run database Migrations
 4. Set up initial semaphore user & password

 > DB Hostname (default 127.0.0.1:3306): 127.0.0.1:3306
 > DB User (default root): root
 > DB Password: toor
 > DB Name (default semaphore): semaphore
 > Playbook path (default /tmp/semaphore): /home/rasputin/playbooks
 > Web root URL (optional, example http://localhost:8010/): http://192.168.2.100:8010/
 > Enable email alerts (y/n, default n): n
 > Enable telegram alerts (y/n, default n): n
 > Enable LDAP authentication (y/n, default n): n

 Generated configuration:
 {
        "mysql": {
                "host": "127.0.0.1:3306",
                "user": "root",
                "pass": "toor",
                "name": "semaphore"
        },
        "port": "",
        "tmp_path": "/home/rasputin/playbooks",
        "cookie_hash": "PL1WhZJJZ7KKRcLHAd8cebx82+LPNAsTPE79tNGQ32o=",
        "cookie_encryption": "tT2hodfYqckUNsC9IeF/M0E/W6NzyR/ty7+gBA37K8o=",
        "email_sender": "",
        "email_host": "",
        "email_port": "",
        "web_host": "http://192.168.2.100:8010/",
        "ldap_binddn": "",
        "ldap_bindpassword": "",
        "ldap_server": "",
        "ldap_searchdn": "",
        "ldap_searchfilter": "",
        "ldap_mappings": {
                "dn": "",
                "mail": "",
                "uid": "",
                "cn": ""
        },
        "telegram_chat": "",
        "telegram_token": "",
        "concurrency_mode": "",
        "max_parallel_tasks": 0,
        "email_alert": false,
        "telegram_alert": false,
        "ldap_enable": false,
        "ldap_enable": false,
        "ldap_needtls": false
 }

 > Is this correct? (yes/no): yes
 > Config output directory (default /root): /root
 Running: mkdir -p /root..
 Configuration written to /root/config.json..
 Pinging db..

 Running DB Migrations..
Checking DB migrations
Creating migrations table
Executing migration v0.0.0 (at 2019-03-13 13:56:17.135736098 +0100 CET m=+214.712393508)...
 [11/11]
Executing migration v1.0.0 (at 2019-03-13 13:56:17.200166993 +0100 CET m=+214.776824388)...
 [7/7]
Executing migration v1.1.0 (at 2019-03-13 13:56:17.355522169 +0100 CET m=+214.932179538)...
 [1/1]
Executing migration v1.2.0 (at 2019-03-13 13:56:17.367823076 +0100 CET m=+214.944480449)...
 [1/1]
Executing migration v1.3.0 (at 2019-03-13 13:56:17.374806985 +0100 CET m=+214.951464365)...
 [3/3]
Executing migration v1.4.0 (at 2019-03-13 13:56:17.42232979 +0100 CET m=+214.998987190)...
 [2/2]
Executing migration v1.5.0 (at 2019-03-13 13:56:17.461199709 +0100 CET m=+215.037857148)...
 [1/1]
Executing migration v0.1.0 (at 2019-03-13 13:56:17.48707641 +0100 CET m=+215.063733781)...
 [6/6]
Executing migration v1.6.0 (at 2019-03-13 13:56:17.530711262 +0100 CET m=+215.107368677)...
 [4/4]
Executing migration v1.7.0 (at 2019-03-13 13:56:17.587992416 +0100 CET m=+215.164649733)...
 [1/1]
Executing migration v1.8.0 (at 2019-03-13 13:56:17.598386373 +0100 CET m=+215.175043678)...
 [2/2]
Executing migration v1.9.0 (at 2019-03-13 13:56:17.613534144 +0100 CET m=+215.190191487)...
 [2/2]
Executing migration v2.2.1 (at 2019-03-13 13:56:17.625215558 +0100 CET m=+215.201872883)...
 [2/2]
Executing migration v2.3.0 (at 2019-03-13 13:56:17.652725557 +0100 CET m=+215.229382919)...
 [3/3]
Executing migration v2.3.1 (at 2019-03-13 13:56:17.687516679 +0100 CET m=+215.264174043)...
 [1/1]
Executing migration v2.3.2 (at 2019-03-13 13:56:17.704184137 +0100 CET m=+215.280841529)...
 [1/1]
Executing migration v2.4.0 (at 2019-03-13 13:56:17.755708707 +0100 CET m=+215.332366024)...
 [1/1]
Executing migration v2.5.0 (at 2019-03-13 13:56:17.765108948 +0100 CET m=+215.341766252)...
 [1/1]
Migrations Finished

Ganz am Ende des Einrichtens von semaphore bekommt man noch einmal eine Zusammenfassung angezeigt und auch wie semaphore zu starten ist.

> Username: rasputin
 > Email: spam@techgoat.net
WARN[0226] sql: no rows in result set                    level=Warn
 > Your name: rasputin
 > Password: toor

 You are all setup rasputin!
 Re-launch this program pointing to the configuration file

./semaphore -config /root/config.json

 To run as daemon:

nohup ./semaphore -config /root/config.json &

 You can login with 1337@techgoat.net or rasputin.

Damit ist *semaphore* nun erfolgreich eingerichtet und kann gestartet werden.

semaphore verwenden

Ich starte semaphore nicht im Hintergrund um zu schauen was genau passiert.

$ semaphore -config /root/config.json
Using config file: /root/config.json
Semaphore v2.5.1
Port :3000
MySQL root@127.0.0.1:3306 semaphore
Tmp Path (projects home) /home/rasputin/playbooks
Checking DB migrations
 403  14:00:22      22.378µs |   GET     /api/user
 204  14:00:28  457.934978ms |   POST    /api/auth/login
 200  14:00:28   92.243091ms |   GET     /api/user
 200  14:00:28    7.773465ms |   GET     /api/projects
 200  14:00:28    8.431954ms |   GET     /api/events/last
...

Nun lauscht semaphore standardmäßig auf Port 3000.

tcp LISTEN 0 128 :::3000 :::* users:(("semaphore",pid=18334,fd=3))

Im Browser sollte man nun beim aufrufen der der entsprechenden IP mit Portangabe (Bsp.: http://192.168.2.100:3000) eine Login-Maske erscheinen.

Hier kann man sich nun mit den eben gesetzten Zugangsdaten anmelden und kommt so auf das Dashboard, wo einem die Übersicht über die letzten Events und eine Liste der eingerichteten Projekte erwartet.

Ein Projekt einrichten

Wir starten mit einem Klick auf das + bei der Projektliste.
Hier vergibt man einen entsprechenden Namen für das Projekt und klickt auf create.

Das neue Projekt erscheint nun in der Liste und durch Klick auf den Namen gelangt man zu den Einzelheiten.
Als erstes kann sollte man die benötigten Keys einrichten. Seien es SSH-Keys oder Keys für AWS, Google und Co.
Ich habe hier einen SSH_Key eingetragen, welcher auch auf github entsprechend hinterlegt ist.
Natürlich sollte man mit dem hinterlegten Keys auch auf die entsprechenden Systeme, welche etwas später im inventory festgelegt sind.
Hierzu klickt man auf Key Store —> create key und trägt die entsprechenden Infos ein.

Anschließend richtet man sich ein Playbook Repository ein, indem man auf Playbook Repositories —> create repository klickt und neben einen eindeutigen Namen trägt man auch die URL zu dem Repo mit den Playbooks ein.
Hier gibt man auch den eben eingetragenen SSH-Key an und klickt abschließend auf create.

Nun legt man unter Inventory noch ein entsprechendes inventory-file an, es kann auch ein vorhandenes verwendet werden.
Dabei handelt es sich quasi um die Zielsysteme, welche in frei wählbare Gruppen aufgeteilt werden können.
Dies geschieht mit Klicks auf Inventory —> create Inventory.
Type Static lässt einem eine feste Liste anlegen, während bei Type File ein vorhandenes inventory verwendet werden kann.
Abschließend klickt man auf create um den Schritt abzuschließen.

Nun geht es an das einrichten des eigentlichen Tasks…

Hierfür klicket man auf Task Templates —> new template und trägt hier einen Alias ein, gibt den Namen des Playbooks aus dem Repo an welches ausgeführt werden soll und wählt noch die vorher eingerichteten SSH-Keys, Playbook Repoisitory und Inventory aus.
Zusätzlich lassen sich im unteren Textfeld Extra CLI Arguments weitere Parameter und Argumente eintragen.

Um nun das im Task Template hinterlegte Ansible-Playbook aus dem entsprechenden github-repo zu starten, klickt man im Task Template bei entsprechenden Task auf run.

Hier hat man nun noch einmal die Möglichkeit ein anderes Playbook oder auch noch weitere Enviroment Variablen anzugeben und entwender erst einen dry run (trestlauf, ohne wirkliche ausführung der Aktionen@ durchführen oder gleich richtig, per klick auf run! zu starten.
Zusätzlich kann man den erweiterten Debug-Modus (-vvvv) aktivieren um eine möglichst ausführliche Ausgabe zu erzeugen.

Im nachfolgenden Fenster erscheint nun die Live-Ausgabe des Logs mit Zeitstempel:

Fazit

Die durch semaphore bereitgestellte Oberfläche und Funktionalität lässt sich auch durch andere Tools, wie z.B. Jenkins oder rundeck abbilden.
Alles in allem ist semaphore wirklich nur das, was sie auch behaupten zu sein:

Autor
Kategorien Ansible, Automatisierung

PRTG Map