Laravel Deployment mit PHPCI und Forge
Um eine Laravel Anwendung auf das Produktivsystem ausrollen zu können, gibt es viele Möglichkeiten. Zur Auswahl stehen eine Reihe von Tools und Lösungen, die für diese Aufgabe geeignet sind: Der Laravel eigene Task Runner Envoy, die Ruby Anwendung Capistrano oder die im Laravel Ecosystem angesiedelte Serververwaltung Forge sind nur ein paar Tools, aus denen man je nach Anforderung das passende auswählen kann. Wie jedoch PHPCI für das Deployment einer Laravel Anwendung verwendet werden kann, zeigt dieser Artikel.

PHPCI

Im ersten Artikel zu PHPCI habe ich bereits die grundlegende Funktionsweise des CI Tools beschrieben und eine beispielhafte Konfiguration erläutert. In diesem zweiten Teil soll es darum gehen, PHPCI in den Deployment Prozess einer Laravel Anwendung einzubinden. Ziel dabei soll sein, mit Hilfe von PHPCI die Codequalität der Anwendung zu kontrollieren als auch sicherzustellen, dass alle Tests in der Anwendung fehlerfrei durchgeführt werden. Im Anschluss werden die Änderungen an der Anwendung auf das Zielsystem veröffentlicht.

Laravel Forge

Für den Deployment Prozess kommt Laravel Forge zum Einsatz, was letztendlich dafür verantwortlich ist, die Anwendung auf dem Produktivsystem zu aktualisieren. Hier ist natürlich jede andere Art von Lösung denkbar, denn Laravel Forge ist für den Einsatz von PHPCI kein Muss und kann daher flexibel in den eigenen Deployment Prozess angepasst werden.

PHPCI meets Laravel

Wie ebenfalls im ersten Artikel zu PHPCI erwähnt, bietet das CI Tool eine flexible Möglichkeit, den Funktionsumfang in Form von Plugins zu erweitern. Um ideal eine Laravel Anwendung in den PHPCI Buildprozess einbinden zu können, habe ich zwei passende Plugins entwickelt, die über composer installiert und der PHPCI Installation hinzugefügt werden können.

Laravel External Enviroment

In der Regel werden anwendungsspezifische Konfigurationseinstellungen in einer .env Datei gespeichert. Da diese Datei jedoch aus Sicherheitsgründen nicht Bestandteil des Git-Repositories ist, ist die Anwendung ohne diese Datei zunächst nicht lauffähig. Enthält die Anwendung Integrationstests, die eine Datenbank erfordern, ist natürlich eine funktionsfähige Anwendung notwendig. Bevor im Deploymentprozess also die Unit Tests ausgeführt werden können, muss eine passende .env Datei dem jeweiligen Buildverzeichnis hinzugefügt werden.

Hier kommt das Plugin zum Einsatz: Es bietet die Möglichkeit, eine externe .env Datei in den jeweiligen Buildprozess einzubinden. Auf dieser Weise müssen keine sensitive Daten in keiner der Konfigurationsdateien (wie zum Beispiel phpci.yml oder phpunit.xml) eingefügt werden.

Installiert wird das Plugin via composer:

composer require rephlux/phpci-external-env

Das Plugin wird nach erfolgreicher Installation in der Liste installierter Plugins angezeigt. Diese Liste ist in PHPCI im Bereich Admin Options -> Plugins zu finden.

Alternativ ist das Plugin auf Github zu finden.

Laravel Remote Deployment

Mit Hilfe des zweiten Plugins für PHPCI kann ein Remote Deployment angestoßen werden, sobald der Build in PHPCI fehlerfrei erstellt wurde. In diesem Beispiel wird der Deployment Hook von Laravel Forge verwendet.

Auch das zweite Plugin wird via composer installiert:

composer require rephlux/phpci-remote-deployment

Das zweite Plugin ist ebenfalls auf Github verfügbar.

Anpassung der phpci.yml

Um die beiden Plugins für den Buildprozess nutzen zu können, muss die phpci.yml Konfigurationsdatei angepasst werden. Das folgende Codebeispiel zeigt einen Auszug aus der phpci.yml mit den entsprechenden Angaben für die neu installierten Plugins:

build_settings:
    ignore:
        - "bootstrap"
        - "database"
        # ...

setup:
    # ...
    \Rephlux\PHPCI\Plugin\ExternalEnvironment:
        master:
            env: "/home/forge/mydomain.com/.env"

test:
    php_unit:

    php_code_sniffer:
    
    # ...

success:
    \Rephlux\PHPCI\Plugin\RemoteDeployment:
        master:
            url: "https://forge.laravel.com/servers/123/sites/456/deploy/http?token=789"

Zunächst wird in der setup Phase der entsprechende Pfad zur .env Datei angegeben, Diese ist zuvor manuell auf dem Server anzulegen. Sollte PHPCI auf dem selben Server betrieben werden, wie die jeweilige Anwendung, dann kann natürlich direkt der Pfad zur entsprechenden .envDatei angegeben werden.

In der successPhase wird als zweites der Pfad zum externen Deployment Hook angegeben. Wie bereits erwähnt kommt Laravel Forge zum Einsatz. An dieser Stelle kann jedoch jedes andere Tool verwendet werden. Der Aufruf des Deployment Hooks kann wahlweise über GET als auch über POST erfolgen. Näheres zur Konfiguration des Plugins ist in der Plugin Dokumentation zu finden.

Über die Angabe des jeweiligen Git-Branches können bei beiden Plugins flexibel unterschiedliche Versionen der Anwendung mit passenden Konfigurationseinstellungen versehen werden. So ist es möglich, für verschiedene Server (Test, Stage, Live) verschiedene Konfigurationen anzugeben, die wiederum auf einen bestimmten Branch im Git-Repository verweisen.

In der Beispiel Konfiguration wird der master-Branch mit der Live-Version der Anwendung verbunden. Der Development-Branch könnte für eine Staging-Version verwendet werden, um so auch aktuelle Anpassungen auf dem Zielsystem deployen zu können, bevor diese in die Produktiv-Umgebung eingebunden werden.

PHPCI Webhook

Neue Builds können in PHPCI über zwei Wege passieren: Manuell und automatisiert. Für ein CI System ist sicherlich die zweite Variante interessant, da so das meiste im Hintergrund automatisiert passiert und für jeden Commit-Vorgang auf einen entsprechenden Branch ein passender Build erzeugt wird.

Um den Buildprozess in PHPCI automatisiert anzustoßen, muss im VCS-Dienst die URL zum PHPCI Webhook eingestellt werden.

Der Ablauf in der Zusammenfassung

Nachdem die Konfiguration aller Bestandteile abgeschlossen ist, sieht der Ablauf wie folgt aus:

  • Durchführung von Anpassungen in der jeweiligen Anwendung mit anschließendem Commit
  • VCS-Dienst stößt über den PHPCI-Webhook den Buildprozess an
  • In der Setup-Phase von PHPCI wird die angegebene .env Datei in den Buildordner geladen
  • Alle in der phpci.yml konfigurierten Tests werden durchgeführt
  • Nach erfolgreichem Test wird das Remote Deployment aus PHPCI heraus angestoßen
  • Laravel Forge beginnt mit dem Deployment und führt die in Forge konfigurierten Deployment Aufgaben durch

Nach Abschluss sind die durchgeführten Anpassungen auf dem entsprechenden Zielsystem ausgerollt. Über PHPCI wurde im Vorfeld jedoch die Qualität der Anwendung überprüft. Sollte im PHPCI Buildprozess ein Fehler auftreten, so wird die Anwendung nicht auf das Zielsystem ausgerollt. So ist zu jederzeit die Qualität der Anwendung gewährleistet. Wenn die Abdeckung an automatisierten Unit-, Acceptance, und/oder Functional-Tests hoch und gut ist, werden da durch Fehler auf dem Zielsystem verringert.