Mailversand mit PHP aus einem Docker-Container

Wie in den letzten Artikeln beschrieben, läuft WordPress im Docker-Container bzw. im Docker Swarm Mode. Auf den meisten Web-Sites gibt es eine Möglichkeit, Kontakt aufzunehmen, beispielsweise per Kontaktformular. Im einfachsten Fall werden die eingegebenen Daten gesammelt und dem Betreiber der Web-Site per Mail zugestellt. Unter WordPress kann ein derartiges Kontaktformular z.B. mit dem Plugin “Contact Form 7” realisiert werden. Ein erster Test war jedoch zunächst nicht erfolgreich, das Formular konnte nicht abgeschickt werden, und die Fehlermeldung war nicht sonderlich aussagekräftig.

Mailversand mit PHP

Nun gibt es in PHP mehrere Möglichkeiten, eine Mail zu versenden. PHP bietet z.B. die Funktion mail(), die letztlich nichts anderes macht, als die übergebenen Parameter wie Empfänger, Nachricht und weitere Header-Angaben (worin sich etwa eine benutzerdefinierte Absenderadresse verbergen kann) einem lokal verfügbaren Programm zu übergeben. Das kann etwa Sendmail sein, oder auch Postfix, wobei es unter Linux bzw. Unix darauf ankommt, dass das Programm, was die Angaben entgegen nimmt, unter einem bestimmten Pfad verfügbar ist. Dieser Pfad kann wiederum per php.ini definiert werden. Unter Windows sieht es wiederum anders aus, dort wird ein MTA (Mail Transport Agent) benötigt, d.h. ein klassischer Mailserver, der auf einem bestimmten Socket lauscht. Kurzum – die Situation ist etwas suboptimal, daher existieren auch Libraries wie SwiftMailer oder zend-mail, die sowohl die Mail-Generierung als auch den Mailversand etwas komfortabler werden lassen und insbesondere für den Mailversand verschiedene Optionen bieten.

Mailversand mit WordPress

WordPress selbst setzt auf PHPMailer, wobei die Konfiguration etwas suboptimal ist. Im speziellen Fall existieren wiederum Plugins wie “WP Mail SMTP“, mit denen der Transportweg der Mail modifiziert werden kann.

So kann statt der Standard-Methode mit den PHP-eigenen Funktionen ein SMTP-Server angesprochen werden, wobei zusätzlich Default-Konfigurationen für Gmail, Mailgun und Sendgrid existieren, letztere dürften hierzulande weniger gebräuchlich sein. Praktisch ist ebenfalls die Möglichkeit, den Versand einer Mail aus WordPress zu testen, ohne jedes Mal ein Kontaktformular oder ähnliches abschicken zu müssen. Insofern hätte das Plugin eine Lösung sein können, sie wäre jedoch auf WordPress beschränkt gewesen. Bei Nutzung anderer Anwendungen, Frameworks oder allgemein PHP-Skripten hätten insofern andere Lösungen verwendet werden müssen. Ein allgemeinerer Ansatz musste hier.

Mailversand aus dem Docker-Container

Die erste Idee bestand darin, tatsächlich einen SMTP-Server bzw. MTA innerhalb des PHP-Docker-Containers einzurichten. Nur widerspricht genau dies dem Gedanken, dass in einem Container nur ein Server-Dienst gestartet werden sollte. Einen zusätzlicher Postfix- oder Sendmail-Dienst auf demselben Host zu starten, entsprach jedoch ebenfalls nicht meinen Vorstellungen – es wäre verbunden gewesen mit zusätzlichem Konfigurationsaufwand, etwa um den Mail-Server erstmal nur lokal lauffähig und sicher zu betreiben, andererseits wäre der Overhead vergleichsweise hoch gewesen, denn letztlich hätte für jeden Docker-Stack dem Schema folgend wiederum ein eigener Mail-Server eingerichtet werden müssen. Letztlich würde es jedoch ausreichen, der PHP-Installation ein Programm anzubieten, was den Mailversand übernimmt. Ein vollständiger Mailserver ist dazu gar nicht notwendig. Eine Lösung für den Mailversand bietet das Programm sSMTP. Es nimmt Mails lokal entgegen und versendet diese an einen (entfernten) Mailserver. Die Konfiguration ist dabei relativ simpel und wird durch eine Datei /etc/ssmtp/ssmtp.conf erledigt. Der Vorteil gegenüber eines vollständigen Mail-Servers bzw. MTAs besteht darin, dass innerhalb des Docker-Containers kein zusätzlicher Dienst gestartet werden muss. Des Weiteren ist keine Änderung gegenüber der Standard-Konfiguration von PHP notwendig, da sSMTP sich auf dem Standard-Pfad von sendmail einrichtet. Die aktuelle Version des php-fpm-swrm-Images beinhaltet bereits sSMTP, in einem entsprechenden Container stellt es sich wie folgt dar:

Somit ist “sendmail” ein symbolischer Link auf die Binärdatei von sSMTP. Zwar existiert eine Default-Konfigurationsdatei /etc/ssmtp/ssmtp.conf, doch falls nicht eine bestimmte Konfiguration zufällig vorliegt, muss die Datei angepasst werden. Denn in der Konfiguration ist als “mailhub” der Name “mail” genannt. Somit versucht sSMTP beim Mailversand, den Rechnernamen “mail” aufzulösen, was in den meisten Fällen fehlschlagen dürfte. Die Konfiguration beschränkt sich jedoch auf wenige Änderungen, je nach dem, an welchen Mailserver die Mails zugestellt werden sollen. Da ich einen Mailserver betreibe, der die Mails für meine Domains entgegen nimmt, bestand die Anpassung aus der Zeile bzgl. “mailhub“. Die vollständige Datei ssmtp.conf sieht somit wie folgt aus:

Ein Beispiel zur Verwendung der Gmail-Server findet sich auf der Debian-Wiki-Seite

Nun muss nur noch die neue Konfiguration eingebunden werden – wie bei Docker üblich wird die Datei einfach in den Container gemountet. Da hier der PHP-Container zum Einsatz kommt, habe ich die Verzeichnisstruktur einfach wie folgt erweitert:

Im docker-compose-File wird somit die entsprechende, hier letzte Zeile hinzugefügt:

Danach kann einfach der Stack neu gestartet werden, wobei zu beachten ist, dass das aktuelle php-fpm-swrm-Image vorliegen muss:

Fazit

Für den Mailversand aus einem Docker-Container heraus eignet sich ein ressourcenschonender und einfacher Ansatz wie sSMTP sehr gut. Die Konfiguration ist vergleichsweise einfach und somit schnell erledigt. Dabei sollte berücksichtigt werden, dass sSMTP keinen vollwertigen Mailserver ersetzen kann, dies aber auch gar nicht will. Für den Versand von Massen-Mails oder Newslettern ist diese Lösung daher nicht geeignet, wobei sich dann wiederum die Frage stellt, ob Derartiges mit WordPress und/oder PHP überhaupt sinnvoll wäre. 

Ähnliche Beiträge

Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert.

Tags: