Ansible + automatisches git pull in einem Cloud-Cluster virtueller Maschinen

Ansible + automatisches git pull in einem Cloud-Cluster virtueller Maschinen

Guten Tag

Wir haben mehrere Cloud-Cluster mit einer großen Anzahl virtueller Maschinen in jedem. Alle diese Geräte werden bei Hetzner gehostet. In jedem Cluster haben wir eine Master-Maschine, von der ein Snapshot erstellt und automatisch auf alle virtuellen Maschinen im Cluster verteilt wird.

Dieses Schema erlaubt uns nicht, gitlab-runner normal zu verwenden, da viele Probleme entstehen, wenn es viele identische registrierte Runner gibt. Das hat uns zu einem Umweg und zum Schreiben dieses Artikels/Manuels veranlasst.

Wahrscheinlich ist das nicht die beste Praxis, aber diese Lösung erscheint uns als die praktischste und einfachste.

Für das Tutorial bitte unter den Cut.

Erforderliche Pakete auf der Master-Maschine:

  • python
  • git
  • Datei mit SSH-Schlüsseln

Das grundlegende Prinzip der Implementierung eines automatischen git pull auf allen virtuellen Maschinen besteht darin, dass eine Maschine erforderlich ist, auf der Ansible installiert ist. Von dieser Maschine wird Ansible die Befehle git pull und den Neustart des aktualisierten Dienstes senden. Wir haben dafür eine separate virtuelle Maschine außerhalb der Cluster erstellt und darauf installiert:

  • python
  • ansible
  • gitlab-runner

Bezüglich organisatorischer Fragen – es ist notwendig, einen gitlab-runner zu registrieren, ssh-keygen auszuführen und den öffentlichen SSH-Schlüssel dieser Maschine in .ssh/authorized_keys auf der Master-Maschine zu speichern, und den Port 22 auf der Master-Maschine für Ansible zu öffnen.

Jetzt konfigurieren wir Ansible

Da unser Ziel ist, alles zu automatisieren, was möglich ist. In der Datei /etc/ansible/ansible.cfg werden wir die Zeile host_key_checking = False, auskommentieren, damit Ansible keine Bestätigung neuer Maschinen anfordert.

Als Nächstes ist es notwendig, automatisch eine Inventardatei für Ansible zu generieren, aus der es die IP-Adressen der Maschinen abruft, auf denen ein git pull durchgeführt werden soll.

Wir generieren diese Datei mit Hilfe der Hetzner-API, Sie können die Liste der Hosts auch aus Ihrem AWS, Azure, DB entnehmen (Sie haben doch irgendwo eine API, um Ihre laufenden Maschinen anzuzeigen, oder?).

Für Ansible ist die Struktur der Inventardatei von großer Bedeutung, sie sollte wie folgt aussehen:

[Gruppe]
ip-Adresse
ip-Adresse

[Gruppe2]
ip-Adresse
ip-Adresse

Um eine solche Datei zu generieren, erstellen wir ein einfaches Skript (nennen wir es vm_list):

#!/bin/bash
echo [group] > /etc/ansible/cloud_ip &&
"ваш CLI запрос на получение IP запущенных машин в кластере"  >> /etc/ansible/cloud_ip
echo " " >> /etc/ansible/cloud_ip
echo [group2] > /etc/ansible/cloud_ip &&
"ваш CLI запрос на получение IP запущенных машин в другом кластере"  >> /etc/ansible/cloud_ip

Es ist Zeit zu überprüfen, ob Ansible funktioniert und mit der Abholung der IP-Adressen kompatibel ist:

/etc/ansible/./vm_list && ansible -i /etc/ansible/cloud_ip -m shell -a 'hostname' group

Im Output sollten die Hostnamen der Maschinen angezeigt werden, auf denen der Befehl ausgeführt wurde.
Ein paar Worte zur Syntax:

  • /etc/ansible/./vm_list — генерируем список машин
  • -i — absoluter Pfad zur Inventardatei
  • -m — Wir verwenden das shell-Modul in Ansible
  • -a — Argument. Hier kann ein beliebiger Befehl eingegeben werden
  • group — der Name Ihres Clusters. Wenn Sie dies für alle Cluster tun möchten, ändern Sie group in all

Weiter geht's — wir versuchen, git pull auf unseren zu machen virtuellen Maschinen:

/etc/ansible/./vm_list && ansible -i /etc/ansible/cloud_ip -m shell -a 'cd /path/to/project && git pull' group 

Wenn wir in der Ausgabe bereits auf dem neuesten Stand oder die Entladung aus dem Repository sehen, funktioniert alles.

Jetzt zu dem, wofür das alles gedacht war

Wir werden unser Skript so einrichten, dass es automatisch bei einem Commit im Master-Branch in GitLab ausgeführt wird

Zuerst machen wir unser Skript schöner und stecken es in eine ausführbare Datei (wir nennen sie exec_pull) —

#!/bin/bash

/etc/ansible/./get_vms && ansible -i /etc/ansible/cloud_ip -m shell -a "$@"

Wir gehen zu unserem GitLab und erstellen die Datei im Projekt .gitlab-ci.yml
Wir fügen folgendes ein:

variables:
  GIT_STRATEGY: none
  VM_GROUP: group

stages:
  - pull
  - restart

run_exec_pull:
  stage: pull
  script:
  
   - /etc/ansible/exec_pull 'cd /path/to/project/'$CI_PROJECT_NAME' && git pull' $VM_GROUP
  
  only:
  - master

run_service_restart:
  stage: restart
  script:
 
   - /etc/ansible/exec_pull 'your_app_stop && your_app_start' $VM_GROUP
   
  only:
  - master 

Alles bereit. Jetzt —

  • machen wir einen Commit
  • wir glauben, dass alles funktioniert

Wenn man die .yml in andere Projekte überträgt, reicht es aus, nur den Namen des Dienstes für den Neustart und den Namen des Clusters zu ändern, auf dem die Ansible-Befehle ausgeführt werden.

Quelle: habr.com

60GB SSD 8Gb DDR4