タイトルの通り Docker でサクッと Postfix で SMTPリレーサーバーをした時のメモです。
やりたいこと
Windows で使いたいメーラーが無くて困っていたところ、Spark が待望の Windows 版をリリース。
早速試してみるも、SMTPサーバーの設定ではユーザー認証と SSL/STARTTLS が必須になっている。
一方某環境は SMTPサーバーは port: 25, 認証無しの平文のみ(N/Wのみ制限)で、Spark の思想と相性が悪い。
しかも Spark は送受信ペアで確立したアカウントのみ有効化されるため、
上記の環境では受信専用としても有効化できない。
そのため、Spark と当該SMTP サーバーの間にSMTPリレーサーバーを設置して、
Spark の要件を満たしつつ、既存のSMTPサーバーへメールが送れるようにする。
この SMTP サーバーを Docker でサクッと立てたい。
Docker Postfix
Docker image として boky/postfix を利用することにする。
以下のような docker-compose.yml
を用意する。
通常の用途(ローカルネット内, コンテナ間など) ならばこれで十分な場合が多いかと。
1 2 3 4 5 6 7 8 9 10 11 |
version: "2" services: smtp-relay: image: boky/postfix:latest restart: always ports: - 587:587 environment: - TZ=Asia/Tokyo - ALLOW_EMPTY_SENDER_DOMAINS=true - RELAYHOST=smtp-server:port |
docker 内外でやりとりするポート(587)、RELAYHOST(smtp-server:port) の設定は自分の環境に合わせて変更する。
動作確認
telnet を使って以下のように確認できる。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
$ telnet localhost 587 Trying 127.0.0.1... Connected to localhost.localdomain. Escape character is '^]'. 220 xxxx ESMTP Postfix HELO hoge 250 xxxx MAIL FROM: from@hoge.jp 250 2.1.0 Ok RCPT TO: to@fuga.jp 250 2.1.5 Ok DATA 354 End data with <CR><LF>.<CR><LF> From: from@hoge.jp Subject: Test mail Hello, World!! . QUIT |
うまく設定できていれば to@fuga.jp
宛に from@hoge.jp
から 件名: Test mail なメールが届く。
Spark 対応確認
しかしこの状態では Spark の SMTP 設定は通らない。
telnet から EHLO
で拡張機能を調べることで確認できる。
1 2 3 4 5 6 |
$ telnet localhost 587 ... EHLO hoge ... 250-STARTTLS (STARTTLS に対応している場合) ... |
或いは openssl を用いて以下のように確認することもできる。
1 2 3 4 |
$ openssl s_client -connect localhost:587 -starttls smtp CONNECTED(00000003) Didn't find STARTTLS in server response, trying anyway... ... |
Spark 対応
通称 "オレオレ証明書" でやってみる。
1 |
$ openssl req -new -x509 -days 365 -nodes -newkey rsa:2048 -keyout private.key -out public.cert |
生成されたファイルを例えば以下のように置く。
./docker-compose.yml
./cert/tls/certs/public.cert
./cert/tls/private/private.key
docker-compose.yml を更新する。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
version: "2" services: smtp-relay: image: boky/postfix:latest restart: always ports: - 587:587 volumes: - ./cert:/etc/pki environment: - TZ=Asia/Tokyo - ALLOW_EMPTY_SENDER_DOMAINS=true - RELAYHOST=smtp-relay:port - POSTFIX_smtpd_use_tls=yes - POSTFIX_smtpd_tls_cert_file=/etc/pki/tls/certs/public.cert - POSTFIX_smtpd_tls_key_file=/etc/pki/tls/private/private.key - POSTFIX_smtpd_tls_security_level=may - SMTPD_SASL_USERS=testuser:hogefuga |
volumes
で先ほど生成した証明書類をコンテナ内に共有し、POSTFIX_smtpd_*
でそれらを適用。
SMTPD_SASL_USERS
は認証情報を id:passwd
の形式で記載。
これで先ほどの telnet
や openssl
を用いた Spark対応確認を行うと、
STARTTLS に対応していることが確認できる。
Spark の SMTP 設定
設定 → アカウント → アカウントを追加 から適切なメールアドレスを入力。
今回のようなオンプレメールの場合は "手動設定" の IMAP/SMTP 設定の画面が出るので、最下部の「詳細設定」を選択。
下部の「送信サーバー(SMTP)」設定の項に以下のように入力する。
- 名前:
SMTPD_SASL_USERS
で指定した id (上記の例では testuser) - メールのパスワード:
SMTPD_SASL_USERS
で指定した passwd (上記の例では hogefuga) - サーバー: 作成した postfixコンテナが動作している docker ホスト(localhost など)
- ポート番号:
docker-compose.yml
で指定した公開ポート (上記の例では 587) - 保護: STARTTLS
以上を入力して「ログイン」を押下すると「証明書が無効化期限切れで安全でない〜」的な事を言われるが、
自分で生成したオレオレ証明書を使っているからに他ならないので「信頼」する。
ここまで設定するとアカウントの設定が完了し、メールの送受信が共にできるようになります。
(引きつづき証明書に関する警告はアカウント設定に表示され続けるが。)
後片付け
docker で公開しているポートは、(特に設定していなければ) ネットワーク上のどこからでもアクセス可能なので、
望まぬ別マシンからアクセスされないように適切にフタをしておく。
例えば、iptables などで透過したい接続元を ACCEPT した後、他の一切の TCP:587 へのパケットを DROP させる。