📧

PHP-FPMのDockerコンテナにPostfixをインストールしてmb_send_mailでメール送信したい

2021/12/25に公開

課題

PHP-FPMベースのDockerコンテナにPostfixをインストールしたい。
PostfixでSMTPリレーでメールを送信したい。
PHPのmb_send_mail関数を用いてメール送信をしたい。

はじめに

前回、『UbuntuのDockerコンテナにPostfixをインストールする』という記事を書きました。
今回の記事はその応用編みたいな感じなので内容は似ています。
PHP-FPMベースに特有のことに焦点をあてて記事を書いています。
基本的なことは省いて説明しているので、もう少し詳しい説明を読みたい方は前回の記事もご覧ください。

解決策

コードを見たほうが早いと思うので、以下にコードとその説明を書きます。

ここに書いたコードと全く同じ実装例を、githubの私のリポジトリにあげておいたので、その方が見やすいという方は使って下さい。

また、SMTPリレーのメール送信のテストにはMailtrapを使いました。

ディレクトリ構成

┏docker-compose.yml
┣Dockerfile
┣entrypoint.sh
┗/configs
  ┣ main.cf
  ┗ sasl_passwd

docker-compose.yml

docker-compose.yml
version: '3.8'
services:
  docker-phpfpm-postfix-example:
    build:
      context: ./
      dockerfile: Dockerfile
    image: docker-phpfpm-postfix-example-image:latest
    container_name: docker-phpfpm-postfix-example-container
    volumes:
      # Postfixの設定をマウントする
      - type: bind
        source: ./configs/main.cf
        target: /etc/postfix/main.cf
      # SASL認証のパスワードをマウントする
      - type: bind
        source: ./configs/sasl_passwd
        target: /etc/postfix/sasl_passwd

Dockerfile

Dockerfile
FROM php:8.1-fpm

# postfixをインストールする為に、パッケージを更新
RUN apt update && apt upgrade -y

# postfixをインストール
RUN DEBIAN_FRONTEND=noninteractive apt install postfix -y

# SMTPリレーにはSMTP AUTHが必要。
# SMTP AUTHの為のSASLにはCyrus SaslとCyrus IMAPを使う。
RUN apt install sasl2-bin -y
RUN DEBIAN_FRONTEND=noninteractive apt install cyrus-imapd -y

# コンテナ起動時のスクリプト
COPY ./entrypoint.sh /
ENTRYPOINT ["/entrypoint.sh"]

entrypoint.sh

entrypoint.sh
#!/bin/bash

# postfixの起動
postfix start

# Postfixは/var/spool/postfixにchrootするので、
# 名前解決に際して、/etc/resolv.confではなく/var/spool/postfix/etc/resolv.confを見に行く。
# 従って、/etc/resolv.confをコピーする。
cp /etc/resolv.conf /var/spool/postfix/etc/resolv.conf

# SASL認証用のテーブル作成
chown root:root /etc/postfix/sasl_passwd
postmap /etc/postfix/sasl_passwd

# postfixの設定変更を反映させる
postfix reload

# dockerのbase imageの元々のENTRYPOINTとCMDを実行する
# つまり、php-fpmを起動する
. /usr/local/bin/docker-php-entrypoint php-fpm

最後の一行の. /usr/local/bin/docker-php-entrypoint php-fpmは、php-fpmのベースイメージで定義されたのENTRYPOINTとCMDを実行する処理です。則ちphpサーバーを起動する処理です。詳細については『PHP-FPMのDockerfileのENTRYPOINTやCMDを上書きしたらエラーが起きた』に書いたので、参考にしてみて下さい。

main.cf

利用するSMTPリレーホストに応じて設定して下さい。
Mailtrapに関しては、ログイン後のページにPostfixの設定例があります。設定例をそのままコピペすれば動くと思います。

main.cf
# ログの出力設定
maillog_file = /var/log/mail.log

# SMTPリレーの設定
relayhost = 
smtp_sasl_auth_enable = 
smtp_sasl_mechanism_filter = 
smtp_sasl_security_options = 
smtp_sasl_password_maps = 

sasl_passwd

利用するSMTPリレーホストに応じて認証情報を設定して下さい。
Mailtrapに関しては、ログイン後のページにPostfixの設定例があります。設定例をそのままコピペすれば動くと思います。

sasl_passwd

動かしてみる

Dockerコンテナにログインして、例えば、下記のようなコマンドを実行してみて下さい。

php -r "mb_send_mail('your-email@example.com', 'test subejct', 'test body', 'From: your-email@example.com');"

メールが送信できると思います。

Discussion