Contao mit Ansible verwalten - Teil 1

von Kirsten Roschanski

Update von Contao

Motivation

Inzwischen habe ich gute 50 produktive Contao Installationen und dazu noch mal eine dreistellige Zahl an Installationen für Entwicklungen. Diese sollen/müssen regelmäßig aktualisiert werden, damit ich zum einen alle Sicherheitsupdates eingespielt bekommen und zum anderen damit ich die Weiterentwicklung mitbekomme. Darum habe ich nach einer automatischen Lösung gesucht , die meine tägliche Arbeit erleichtert und sich dabei in meinen bestehenden Workflow integriert. Daher setze ich auf Ansible, das ich bereits seit längerem dazu nutzen meine Server zu warten, pflegen und sogar zu installieren.

Nun also will und kann ich damit auch meine Contao-Installationen aufsetzen. Dank der Contao-Console und des Contao-Manager ist dieses ganz leicht zu realisieren gewesen. Schau es dir aber gerne selber an.

Was ist Ansible?

Ansible ist ein Open-Source Automatisierungs-Werkzeug zur allgemeinen Konfiguration und Administration von Servern. Es kombiniert Softwareverteilung, Ad-hoc-Kommando-Ausführung und Konfigurationsmanagement.

Voraussetzung ist, das man mit SSH auf den Server kommt und auf dem Server Python zur Verfügung steht. Eine zusätzliche Software muss nur auf dem eigenen Rechner bzw. dem zentralen System installiert werden.

Eine gute Einführung gibt es bei geekflare.com wie ich finde.

Vorbereitung

Ich persönlich habe die Dateien alle in einem Verzeichnis liegen, wer natürlich noch aufräumen möchte kann dieses gerne machen und sich entsprechende Ordner anlegen. Für die Konfiguration der einzelnen Contao-Installationen habe ich jedoch einem Verzeichnis angelegt. Damit mir die nicht ständig im Weg sind.

Meine Struktur sieht wie folgt aus:

contao-ansible // Verzeichnis für Ansible-Playbooks
  customers // Verzeichnis für Installationen
    kirsten-roschanski.de.yml // Konfig meiner Webseite
  ansible.cfg
  update_base.yml
Tipp

Wenn du, wie ich, mit verschiedenen Bereitstellungsumgebungen arbeitest, dann empfehle ich dir die Ordner entsprechend anzulegen. Das macht es das ganze viel übersichtlicher.

update_base.yml

---
- hosts: all
  tasks:
  - name: 'Show Contao Version'
    command: "{{ php_path }} {{ websitePath }}/vendor/bin/contao-console contao:version"
    register: version
  - debug:
     msg: "Contao Version - {{ version.stdout_lines }}"

  - name: 'Contao-Manager Update'
    shell: "{{ php_path }} -d memory_limit=-1 web/contao-manager.phar.php self-update"
    args:
      chdir: '{{ websitePath }}'
    register: update
  - debug:
     var: update.stdout_lines

  - name: 'Update Contao'
    shell: "{{ php_path }} -d memory_limit=-1 web/contao-manager.phar.php composer update"
    args:
      chdir: '{{ websitePath }}'
    register: update
  - debug:
     var: update.stdout_lines

  - name: 'Datenbankupdate für Contao'
#    command: "{{ php_path }} -d memory_limit=-1 {{ websitePath }}/vendor/bin/contao-console contao:migrate --with-deletes" # Mit löschen der überflüssugen Tabellen und Spalten
    command: "{{ php_path }} -d memory_limit=-1 {{ websitePath }}/vendor/bin/contao-console contao:migrate"
    register: dbupdate
  - debug:
     var: dbupdate.stdout_lines

  - name: 'Show Contao Version'
    command: "{{ php_path }} {{ websitePath }}/vendor/bin/contao-console contao:version"
    register: version
  - debug:
      msg: "Contao Version - {{ version.stdout_lines }}"

Was macht dieses Playbook?

Es werden 5 Tasks abgearbeitet:

  1. Es wird die aktuelle Version ausgelesen und ausgegeben.
  2. Der Contao-Manager wird auf die aktuelle Version aktualisiert. Ausgabe über Update oder das er bereits aktuell ist.
  3. Contao-Installation wird aktualisiert.
  4. Die Datenbank wird aktualisiert (ohne löschen).
  5. Die nun aktuelle Version wird ausgelesen und ausgegeben.

ansible.cfg

[defaults]
force_color = false
force_handlers = True
nocows = 1
inventory = customers

[persistent_connection]
command_timeout = 10

[ssh_connection]
pipelining = True
control_path = /tmp/ansible-ssh-%%h-%%p-%%r
ssh_args = -o ControlMaster=auto -o ControlPersist=60s
Information

Die Konfiguration umfasst bereits einige Werte, die für Updates nicht notwendig sind, sondern in dem nächsten Teil der Installation benötigt werden.

customers/kirsten-roschanski.de.yml

privat:# Einzigartigen Namen, damit die Variablen nicht überschrieben werden
  hosts:
    kirsten-roschanski.de:
  vars:
    ansible_user: www-data
    ansible_python_interpreter: /usr/bin/env python3

    php_path: /usr/bin/php7.4
    websitePath: /var/www/html/kirsten-roschanski.de

    ## DATABASE
    database_host: localhost
    database_port: 3306
    database_user: mysql1
    database_password: meinmySQLPasswort
    database_name: mysql1

    ## CONTAO INSTALL
    installPassword: meinInstallPassword

    ## CONTAO-CONFIG
    adminEmail: kirsten@kirsten-roschanski.de
    websiteTitle: "Kirsten Roschanski"
    contao_version: "4.9"
    contao_modules:
      - "contao/news-bundle"
      - "contao/newsletter-bundle"
      - "lindesbs/climan"
      - "terminal42/notification_center"
      - "erdmannfreunde/euf_nutshell"
      - "erdmannfreunde/theme-toolbox"
      - "erdmannfreunde/euf_contact"
      - "erdmannfreunde/contao-grid-bundle"
      - "erdmannfreunde/euf_hero"
      - "erdmannfreunde/portfoliobundle"

    ## CONTAO-MANAGER
    contao_manager_user: administartor
    contao_manager_pass: meinManagerPassword

    ## CONTAO-Benutzer
    users:
     - ["kroschanski", "Kirsten Roschanski", "kirsten@kirsten-roschanski.de", "defaultPassword", "de", "--admin"]

Wie führe ich das nun aus?

Wenn ich nur eine Installation aktualisieren möchte, dann nutze ich folgenden Befehl:

ansible-playbook -i customers/kirsten-roschanski.de.yml update_base.yml

dieses kann ich nur machen, da mein SSH-Key auf dem Server hinterlegt ist. Wenn ich das Passwort eingeben muss, dann rufe ich das mit der Option -k auf:

ansible-playbook -i customers/kirsten-roschanski.de.yml -k update_base.yml

Da ich aber mehre Installationen mit einem mal aktualisieren möchte, lasse ich die Angabe für die Installation weg:

ansible-playbook update_base.yml

Das geht nur weil wir in der ansible.cfg den Ordner angegeben haben. Wenn man nun verschiedene Kundengruppen macht, dann kann mit -i Ordnername auch diese Gruppe angesprochen werden.

Wie geht es weiter?

Im nächsten Teil zeige ich in einem Playbook wie ich voll automatisch eine Contao-Installation mache.