LinuxのmailコマンドでSMTPサーバを使ってメール送信する (from GCE/nagios)

情報ソースとして割とあふれている話なんですが、前提が足りない情報が多いので、補足すべく書いておきます。
と、その前に、mail コマンドで SMTPサーバ経由のメール送信をやりたくなった、そもそもの動機を書いておきます。


GCE(Google Compute Engine)で作ったサーバに、nagios をセットアップしていて、アラートをメールで飛ばしたい。が、現在はGCE のインスタンスから宛先{25, 465, 587}番ポートへのメール送信は仕様として禁止されている。なので、GCE では sendgrid や mailgun、Google Apps を使ってメール送信してくれ、とドキュメントに記載されているのですが、まぁ色々な事情と対象がアラートメールという性質もあり、GCE 外部で既に動かしているSMTPサーバを経由して送りたい。
で、nagios のメール送信は、内部的に mail コマンドを使っていて、MTA を挟むよりは mail コマンドで完結できれば楽だよねー、ということでタイトル通りのことを実現したいというのがやりたいことです。

ちなみに、接続先となる外部のSMTPサーバで、上記ポート番号は使えない(接続できない)ので、あらかじめ2525番ポート等で LISTEN させておく必要があります。

mailコマンドの "-S" オプションを使う

結論から書いておくと、このオプションを使います。これは、世の中の色々なブログで紹介されている内容で、その通りなのです。
ああ、なるほど、サポートしてるよね。じゃあ試してみようと、GCE で立ち上げた Ubuntu なインスタンスから、意気揚々とコマンドを打つと、

mail: invalid option -- 'S'
Try 'mail --help' or 'mail --usage' for more information.

そんなオプションは無いと。manを読んでみても、確かに "-S" なんてオプションは無い。
他にも、 /etc/mail.rc や .mailrc に "set smtp" で指定すべしという情報もよく見かけるが、こちらも有効にならない。

何が足りなかったのか

上記の Ubuntu なインスタンスで使っていたのは、GNU Mailutils だったのですが、他所のサイトで調べていくと CentOS などでは "yum install mailx" とインストールされていて、ああ、mailutils よりリッチなやつを使うのか、と気づきました。
で、Ubuntu だと apt パッケージで用意されているので。

$ sudo apt-get install heirloom-mailx

とインストールしてから、メールコマンドを実行すると、"-S" オプションを指定することで、問題なくSMTPサーバ経由でメールを送ることができました。

 -S variable[=value]
     Sets the internal option variable and, in case of a value option, assigns value to it.  Even though options set
     via -S may be overwritten from within resource files, the command line setting will be reestablished after all
     resource files have been loaded.

man はこんな感じ。

mailコマンド・オプション例

例として、nagios に設定した commands.cfg の mail コマンドを載せておきます。

# 'notify-host-by-email' command definition
define command{
        command_name    notify-host-by-email
        command_line    /usr/bin/printf "%b" "***** Nagios *****\n\nNotification Type: $NOTIFICATIONTYPE$\nHost: $HOSTNAME$\nState: $HOSTSTATE$\nAddress: $HOSTADDRESS$\nInfo: $HOSTOUTPUT$\n\nDate/Time: $LONGDATETIME$\n" | /usr/bin/mail -s "** $NOTIFICATIONTYPE$ Host Alert: $HOSTNAME$ is $HOSTSTATE$ **" -S "smtp=smtp://(SMTPサーバ名):(ポート)" -r (送信元メールアドレス) $CONTACTEMAIL$
        }

# 'notify-service-by-email' command definition
define command{
        command_name    notify-service-by-email
        command_line    /usr/bin/printf "%b" "***** Nagios *****\n\nNotification Type: $NOTIFICATIONTYPE$\n\nService: $SERVICEDESC$\nHost: $HOSTALIAS$\nAddress: $HOSTADDRESS$\nState: $SERVICESTATE$\n\nDate/Time: $LONGDATETIME$\n\nAdditional Info:\n\n$SERVICEOUTPUT$\n" | /usr/bin/mail -s "** $NOTIFICATIONTYPE$ Service Alert: $HOSTALIAS$/$SERVICEDESC$ is $SERVICESTATE$ **" -S "smtp=smtp://(SMTPサーバ名):(ポート)" -r (送信元メールアドレス) $CONTACTEMAIL$
        }

とまぁ、こんな感じですかね。
それでは!=͟͟͞͞(๑•̀=͟͟͞͞(๑•̀д•́=͟͟͞͞(๑•̀д•́๑)=͟͟͞͞(๑•̀д•́


[改訂第3版]Linuxコマンドポケットリファレンス

[改訂第3版]Linuxコマンドポケットリファレンス