Elasticsearch で収集している VTuber の情報を定期的にはてなブログに自動投稿しようかなと思ったのでメールサーバを構築した。久しぶりにやって忘れていたのでメモっておくことにする。CentOS の情報は多いけど Debian 系は少ない。
PRETTY_NAME="Debian GNU/Linux 10 (buster)" NAME="Debian GNU/Linux" VERSION_ID="10" VERSION="10 (buster)" VERSION_CODENAME=buster ID=debian HOME_URL="https://www.debian.org/" SUPPORT_URL="https://www.debian.org/support" BUG_REPORT_URL="https://bugs.debian.org/"
Postfix の設定
必要なパッケージをインストールする。
apt install postfix sasl2-bin bsd-mailx
Google のアカウントで二段階認証不要のアプリ用パスワードを作成しておく。16 文字のパスワードを発行される。
SASL 用のパスワードファイルを作成する。ユーザ名 foo
、アプリケーション用のパスワードが aaaaaaaaaaaaaaaa
の場合は下記のような書式になる。/etc/postfix
に sasl
というディレクトリが出来ているのでその中でもいいと思う。
[smtp.gmail.com]:587 foo@gmail.com:aaaaaaaaaaaaaaaa
平文で書いてあるのでパーミッションを変更しておく。
chmod 0600 /etc/postfix/sasl_passwd
postmap
コマンドで Postfix ルックアップテーブルを作成する。sasl_passwd.db
のようなファイルが作成される。
postmap /etc/postfix/sasl_passwd
main.cf の設定
/etc/postfix/main.cf
に設定を追加する。最低限下記を追加しておけばメールの送信が出来るようになる。
relayhost = [smtp.gmail.com]:587 smtp_sasl_auth_enable = yes smtp_sasl_password_maps = hash:/etc/postfix/sasl_passwd smtp_sasl_tls_security_options = noanonymous smtp_tls_security_level = encrypt
デフォルトからの差分は下記の通り
--- /dev/fd/63 2019-11-17 15:11:02.659286299 +0900 +++ main.cf 2019-11-17 15:10:59.619368408 +0900 @@ -36,9 +36,13 @@ alias_maps = hash:/etc/aliases alias_database = hash:/etc/aliases mydestination = $myhostname, localhost, localhost.localdomain, , localhost -relayhost = +relayhost = [smtp.gmail.com]:587 mynetworks = 127.0.0.0/8 [::ffff:127.0.0.0]/104 [::1]/128 mailbox_size_limit = 0 recipient_delimiter = + inet_interfaces = all inet_protocols = all +smtp_sasl_auth_enable = yes +smtp_sasl_password_maps = hash:/etc/postfix/sasl_passwd +smtp_sasl_tls_security_options = noanonymous +smtp_tls_security_level = encrypt
Postfix を再起動(もしくは設定ファイルを再読み込み)する。
systemctl restart postfix
Postfix パラメータの詳細
デフォルト値は postconf -d
で確認することも出来る。
smtp_sasl_auth_enable (default: no) Enable SASL authentication in the Postfix SMTP client. By default, the Postfix SMTP client uses no authentication. Example: smtp_sasl_auth_enable = yes smtp_sasl_mechanism_filter (default: empty) If non-empty, a Postfix SMTP client filter for the remote SMTP server's list of offered SASL mechanisms. Different client and server implementations may support different mechanism lists; by default, the Postfix SMTP client will use the intersection of the two. smtp_sasl_mechanism_filter specifies an optional third mechanism list to intersect with. Specify mechanism names, "/file/name" patterns or "type:table" lookup tables. The right-hand side result from "type:table" lookups is ignored. Specify "!pattern" to exclude a mechanism name from the list. The form "!/file/name" is supported only in Postfix version 2.4 and later. This feature is available in Postfix 2.2 and later. Examples: smtp_sasl_mechanism_filter = plain, login smtp_sasl_mechanism_filter = /etc/postfix/smtp_mechs smtp_sasl_mechanism_filter = !gssapi, !login, static:rest smtp_sasl_password_maps (default: empty) Optional Postfix SMTP client lookup tables with one username:password entry per sender, remote hostname or next-hop domain. Per-sender lookup is done only when sender-dependent authentication is enabled. If no username:password entry is found, then the Postfix SMTP client will not attempt to authenticate to the remote host. The Postfix SMTP client opens the lookup table before going to chroot jail, so you can leave the password file in /etc/postfix. Specify zero or more "type:name" lookup tables, separated by white‐ space or comma. Tables will be searched in the specified order until a match is found. smtp_sasl_security_options (default: noplaintext, noanonymous) Postfix SMTP client SASL security options; as of Postfix 2.3 the list of available features depends on the SASL client implementation that is selected with smtp_sasl_type. The following security features are defined for the cyrus client SASL implementation: Specify zero or more of the following: noplaintext Disallow methods that use plaintext passwords. noactive Disallow methods subject to active (non-dictionary) attack. nodictionary Disallow methods subject to passive (dictionary) attack. noanonymous Disallow methods that allow anonymous authentication. mutual_auth Only allow methods that provide mutual authentication (not available with SASL version 1). Example: smtp_sasl_security_options = noplaintext smtp_sasl_tls_security_options (default: $smtp_sasl_security_options) The SASL authentication security options that the Postfix SMTP client uses for TLS encrypted SMTP sessions. This feature is available in Postfix 2.2 and later. smtp_tls_security_level (default: empty) The default SMTP TLS security level for the Postfix SMTP client; when a non-empty value is specified, this overrides the obsolete parameters smtp_use_tls, smtp_enforce_tls, and smtp_tls_enforce_peername. Specify one of the following security levels: none No TLS. TLS will not be used unless enabled for specific desti‐ nations via smtp_tls_policy_maps. may Opportunistic TLS. Use TLS if this is supported by the remote SMTP server, otherwise use plaintext. Since sending in the clear is acceptable, demanding stronger than default TLS security merely reduces interoperability. The "smtp_tls_ciphers" and "smtp_tls_protocols" (Postfix >= 2.6) configuration parameters provide control over the protocols and cipher grade used with opportunistic TLS. With earlier releases the opportunistic TLS cipher grade is always "export" and no protocols are disabled. When TLS handshakes fail, the connection is retried with TLS disabled. This allows mail delivery to sites with non-interop‐ erable TLS implementations. encrypt Mandatory TLS encryption. Since a minimum level of security is intended, it is reasonable to be specific about sufficiently secure protocol versions and ciphers. At this security level and higher, the main.cf parameters smtp_tls_mandatory_protocols and smtp_tls_mandatory_ciphers specify the TLS protocols and minimum cipher grade which the administrator considers secure enough for mandatory encrypted sessions. This security level is not an appropriate default for systems delivering mail to the Internet. dane 省略 dane-only 省略 fingerprint 省略 verify 省略 secure 省略 Examples: # No TLS. Formerly: smtp_use_tls=no and smtp_enforce_tls=no. smtp_tls_security_level = none # Opportunistic TLS. smtp_tls_security_level = may # Postfix >= 2.6: # Do not tweak opportunistic ciphers or protocol unless it is essential # to do so (if a security vulnerability is found in the SSL library that # can be mitigated by disabling a particular protocol or raising the # cipher grade from "export" to "low" or "medium"). smtp_tls_ciphers = export smtp_tls_protocols = !SSLv2, !SSLv3 # Mandatory (high-grade) TLS encryption. smtp_tls_security_level = encrypt smtp_tls_mandatory_ciphers = high 以下略
トラブルシュート
■ smtp_sasl_auth_enable = yes
これが無いと Authentication Required.
で失敗する。
Nov 16 08:10:23 debian postfix/smtp[5891]: 49F92409EE: to=foo@gmail.com, relay=smtp.gmail.com[74.125.204.108]:587, delay=1, delays=0.01/0/0.82/0.17, dsn=5.5.1, status=bounced (host smtp.gmail.com[74.125.204.108] said: 530-5.5.1 Authentication Required. Learn more at 530 5.5.1 https://support.google.com/mail/?p=WantAuthError 82sm14466130pfa.115 - gsmtp (in reply to MAIL FROM command))
■ smtp_sasl_password_maps = hash:/path/to/file
これが無いと specify a password table via the `smtp_sasl_password_maps' configuration parameter
で失敗する。
Nov 16 08:17:46 debian postfix/smtp[6345]: fatal: specify a password table via the `smtp_sasl_password_maps' configuration parameter
■ smtp_sasl_tls_security_options = noanonymous
デフォルトの noplaintext, noanonymous
だと弾かれてしまうので noplaintext
を外して noanonymous
だけにする。
Nov 16 08:04:32 debian postfix/smtp[5265]: warning: SASL authentication failure: No worthy mechs found Nov 16 08:04:32 debian postfix/smtp[5265]: 6D638409F6: SASL authentication failed; cannot authenticate to server smtp.gmail.com[108.177.97.108]: no mechanism available Nov 16 08:04:32 debian postfix/smtp[5265]: connect to smtp.gmail.com[2404:6800:4008:c00::6c]:587: Network is unreachable
■ smtp_tls_security_level = encrypt
デフォルトが empty
なので Must issue a STARTTLS command first.
で失敗する。encrypt
ではなく may
でも動くがこちらは TLS 接続に失敗した時にプレーンテキストを使うようなので encrypt
にした。
Nov 16 08:12:56 debian postfix/smtp[6109]: 991C44085B: to=foo@gmail.com, relay=smtp.gmail.com[74.125.204.108]:587, delay=0.65, delays=0.05/0.01/0.41/0.17, dsn=5.7.0, status=bounced (host smtp.gmail.com[74.125.204.108] said: 530 5.7.0 Must issue a STARTTLS command first. y6sm12524933pfm.12 - gsmtp (in reply to MAIL FROM command))
メールの送信
とりあえず適当にメールを送ってみる。
echo "World" | mail -s "Hello" 宛先メールアドレス
特に問題無かったのではてなブログにメール投稿する方法を調べると投稿用と下書き用のメールアドレスで分かれているらしい。
下書き用のメールアドレスにメールを送ってみると何故かタイトルの日本語が文字化けする。調べてみるとタイトルは ISO-2022-JP で出力しなきゃいけないらしい。nkf
コマンドを使ってエンコードする。入力と出力でオプションの大小文字が違う。
Usage: nkf -[flags] [--] [in file] .. [out file for -O flag] j/s/e/w Specify output encoding ISO-2022-JP, Shift_JIS, EUC-JP UTF options is -w[8[0],{16,32}[{B,L}[0]]] J/S/E/W Specify input encoding ISO-2022-JP, Shift_JIS, EUC-JP UTF option is -W[8,[16,32][B,L]] m[BQSN0] MIME decode [B:base64,Q:quoted,S:strict,N:nonstrict,0:no decode] M[BQ] MIME encode [B:base64 Q:quoted] f/F Folding: -f60 or -f or -f60-10 (fold margin 10) F preserve nl Z[0-4] Default/0: Convert JISX0208 Alphabet to ASCII 1: Kankaku to one space 2: to two spaces 3: HTML Entity 4: JISX0208 Katakana to JISX0201 Katakana X,x Convert Halfwidth Katakana to Fullwidth or preserve it O Output to File (DEFAULT 'nkf.out') L[uwm] Line mode u:LF w:CRLF m:CR (DEFAULT noconversion) --ic=<encoding> Specify the input encoding --oc=<encoding> Specify the output encoding --hiragana --katakana Hiragana/Katakana Conversion --katakana-hiragana Converts each other --{cap, url}-input Convert hex after ':' or '%' --numchar-input Convert Unicode Character Reference --fb-{skip, html, xml, perl, java, subchar} Specify unassigned character's replacement --in-place[=SUF] Overwrite original files --overwrite[=SUF] Preserve timestamp of original files -g --guess Guess the input code -v --version Print the version --help/-V Print this help / configuration Network Kanji Filter Version 2.1.5 (2018-12-15) Copyright (C) 1987, FUJITSU LTD. (I.Ichikawa). Copyright (C) 1996-2018, The nkf Project.
ja_JP.UTF-8
とかなら入力に -W
(UTF)付けなくてもいいみたいだけど一応付けておく。
root@debian:~# echo "タイトル" | nkf -MWj =?ISO-2022-JP?B?GyRCJT8lJCVIJWsbKEI=?=
あとはこれを Cron に組み込んではてなブログの投稿用メールアドレスに送れば自動投稿が出来るようになる。
結果
VTuber の一週間の再生回数を土曜日の朝に自動投稿するようにした。週末はここから流行りの VTuber のチャンネルでも観てゆっくり過ごしたい。