Mail Server Administration
メールサーバ管理 (Mail Server Administration) 包括ガイド
目次
- はじめに
- メールの基礎知識
- Postfix によるメール送信サーバ構築
- 3.1 Postfix アーキテクチャ
- 3.2 main.cf の主要設定
- 3.3 仮想ドメインと仮想ユーザ
- 3.4 トランスポートマップ
- 3.5 リレーホスト設定
- 3.6 TLS/SSL 設定
- 3.7 スパムフィルタリングとアクセス制御
- Dovecot による受信サーバ構築
- 4.1 Dovecot アーキテクチャ
- 4.2 IMAP/POP3 設定
- 4.3 メールボックス形式 (Maildir vs mbox)
- 4.4 認証設定
- 4.5 SSL/TLS 設定
- メールキュー管理
- 5.1 mailq / postqueue
- 5.2 postsuper によるキュー操作
- 5.3 キュー監視とアラート
- スパム対策
- 6.1 SpamAssassin
- 6.2 OpenDKIM
- 6.3 Postscreen と Greylisting
- トラブルシューティング
- プロトコル・ポート比較表
- ベストプラクティス
- 参考文献
1. はじめに
メールサーバはインターネット基盤の中核を担うサービスであり、Linux システム管理者にとって不可欠なスキルである。本ガイドでは、MTA (Mail Transfer Agent) としての Postfix、MDA (Mail Delivery Agent) / IMAP/POP3 サーバとしての Dovecot を中心に、送受信サーバの構築・運用・トラブルシューティングを包括的に解説する。
主要コンポーネントの関係:
送信者 MUA ---> MTA (Postfix) ---> インターネット ---> MTA (Postfix)
|
MDA (Dovecot)
|
受信者 MUA
| 略語 | 正式名称 | 役割 | 代表例 |
|---|---|---|---|
| MUA | Mail User Agent | メールクライアント | Thunderbird, Outlook, mutt |
| MTA | Mail Transfer Agent | メール転送 | Postfix, Sendmail, Exim |
| MDA | Mail Delivery Agent | メールボックスへの配送 | Dovecot LDA, Procmail |
| MSA | Mail Submission Agent | ユーザからのメール受付 | Postfix (port 587) |
2. メールの基礎知識
2.1 メール配送の仕組み
[送信者 MUA] --SMTP(587)--> [送信側 MTA] --SMTP(25)--> [受信側 MTA]
|
[MDA / LDA]
|
[メールボックス]
|
[受信者 MUA] <--IMAP(993)/POP3(995)--
- 送信者が MUA でメールを作成し、MSA (ポート 587) に送信
- 送信側 MTA が受信側ドメインの MX レコードを DNS に問い合わせ
- 送信側 MTA が受信側 MTA にポート 25 で SMTP 接続しメールを転送
- 受信側 MTA が MDA を使ってメールボックスに配送
- 受信者が IMAP または POP3 でメールを取得
2.2 プロトコル概要 (SMTP, POP3, IMAP)
SMTP (Simple Mail Transfer Protocol)
$ telnet mail.example.com 25
Trying 192.168.1.10...
Connected to mail.example.com.
Escape character is '^]'.
220 mail.example.com ESMTP Postfix
EHLO client.example.com
250-mail.example.com
250-PIPELINING
250-SIZE 10240000
250-VRFY
250-ETRN
250-STARTTLS
250-AUTH PLAIN LOGIN
250-AUTH=PLAIN LOGIN
250-ENHANCEDSTATUSCODES
250-8BITMIME
250-DSN
250 SMTPUTF8
MAIL FROM:<user@example.com>
250 2.1.0 Ok
RCPT TO:<dest@example.org>
250 2.1.5 Ok
DATA
354 End data with <CR><LF>.<CR><LF>
Subject: Test Mail
From: user@example.com
To: dest@example.org
This is a test message.
.
250 2.0.0 Ok: queued as ABC12345
QUIT
221 2.0.0 Bye
POP3 vs IMAP 比較
| 項目 | POP3 | IMAP |
|---|---|---|
| ポート (平文) | 110 | 143 |
| ポート (SSL/TLS) | 995 | 993 |
| メール保存場所 | クライアント側 | サーバ側 |
| マルチデバイス | 不向き | 適している |
| フォルダ管理 | 非対応 | 対応 |
| オフライン利用 | 容易 | キャッシュ依存 |
| サーバ負荷 | 低い | 高い |
| 帯域消費 | 初回大きい | ヘッダのみ取得可 |
| 用途 | 単一端末 | 複数端末・組織利用 |
2.3 DNS とメール (MX レコード)
MX レコードはドメインのメール受信先を指定する DNS レコードである。
$ dig MX example.com +short
10 mail1.example.com.
20 mail2.example.com.
$ dig TXT example.com +short
"v=spf1 mx ip4:192.168.1.0/24 -all"
MX レコードの優先度: 数値が小さいほど優先度が高い。上記の例では mail1 が優先的に使用され、接続不可の場合に mail2 にフォールバックする。
2.4 メール認証技術 (SPF, DKIM, DMARC)
SPF (Sender Policy Framework)
送信元 IP アドレスの正当性を検証する仕組み。
;; DNS TXT レコード
example.com. IN TXT "v=spf1 mx ip4:203.0.113.0/24 include:_spf.google.com -all"
| 修飾子 | 意味 | 動作 |
|---|---|---|
+ | Pass | 許可 (デフォルト) |
- | Fail | 拒否 |
~ | SoftFail | 受け入れるがマーク |
? | Neutral | 判定しない |
DKIM (DomainKeys Identified Mail)
送信メールに電子署名を付与し、メールの改ざんを検知する仕組み。
;; DNS TXT レコード
selector1._domainkey.example.com. IN TXT "v=DKIM1; k=rsa; p=MIIBIjANBg..."
メールヘッダでの署名例:
DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
d=example.com; s=selector1;
h=from:to:subject:date:message-id;
bh=ABC123...;
b=XYZ789...
DMARC (Domain-based Message Authentication, Reporting and Conformance)
SPF と DKIM の結果を基にメールの処理ポリシーを定義する。
;; DNS TXT レコード
_dmarc.example.com. IN TXT "v=DMARC1; p=reject; rua=mailto:dmarc-reports@example.com; ruf=mailto:dmarc-forensic@example.com; pct=100; adkim=s; aspf=s"
| パラメータ | 説明 |
|---|---|
p | ポリシー: none / quarantine / reject |
rua | 集約レポート送信先 |
ruf | フォレンジックレポート送信先 |
pct | ポリシー適用率 (%) |
adkim | DKIM アライメント: s(strict) / r(relaxed) |
aspf | SPF アライメント: s(strict) / r(relaxed) |
認証チェックの全体フロー:
受信メール
|
+-- SPF チェック --> Pass/Fail
|
+-- DKIM チェック --> Pass/Fail
|
+-- DMARC 評価 (SPF + DKIM の結果)
|
+-- none: 何もしない
+-- quarantine: 迷惑メールフォルダへ
+-- reject: 受信拒否
3. Postfix によるメール送信サーバ構築
3.1 Postfix アーキテクチャ
Postfix はモジュール設計の MTA であり、複数のデーモンが協調動作する。
+---------+
インターネット -->| smtpd |--+
+---------+ |
v
+---------+ +---------+ +---------+
ローカル送信 --> | pickup |--> | cleanup |--> | qmgr |
+---------+ +---------+ +---------+
|
+---------------+---------------+
| | |
+---------+ +---------+ +---------+
| smtp | | local | | virtual |
+---------+ +---------+ +---------+
| | |
リモート配送 ローカル配送 仮想ユーザ配送
| デーモン | 役割 |
|---|---|
smtpd | 受信 SMTP 接続の処理 |
pickup | maildrop ディレクトリからのメール取得 |
cleanup | ヘッダの正規化・重複チェック |
qmgr | キューマネージャ (配送スケジューリング) |
smtp | リモートサーバへの配送 |
local | ローカルメールボックスへの配送 |
virtual | 仮想ドメイン・ユーザへの配送 |
3.2 main.cf の主要設定
Postfix の中核設定ファイルは /etc/postfix/main.cf である。
# インストール
$ sudo dnf install postfix # RHEL/Rocky/Alma
$ sudo apt install postfix # Debian/Ubuntu
/etc/postfix/main.cf:
# ==============================
# 基本設定
# ==============================
# ホスト名とドメイン
myhostname = mail.example.com
mydomain = example.com
myorigin = $mydomain
# ネットワーク設定
inet_interfaces = all
inet_protocols = ipv4
# 信頼するネットワーク
mynetworks = 127.0.0.0/8, 10.0.0.0/24
# バナー (バージョン情報を隠す)
smtpd_banner = $myhostname ESMTP
# ==============================
# 配送先設定
# ==============================
mydestination = $myhostname, localhost.$mydomain, localhost, $mydomain
# メールボックス形式
home_mailbox = Maildir/
# メールサイズ制限 (50MB)
message_size_limit = 52428800
# メールボックスサイズ制限 (1GB)
mailbox_size_limit = 1073741824
# ==============================
# SMTP 認証 (SASL)
# ==============================
smtpd_sasl_type = dovecot
smtpd_sasl_path = private/auth
smtpd_sasl_auth_enable = yes
smtpd_sasl_security_options = noanonymous
smtpd_sasl_local_domain = $myhostname
# ==============================
# TLS 設定
# ==============================
smtpd_tls_cert_file = /etc/pki/tls/certs/mail.example.com.crt
smtpd_tls_key_file = /etc/pki/tls/private/mail.example.com.key
smtpd_tls_security_level = may
smtpd_tls_loglevel = 1
smtpd_tls_session_cache_database = btree:${data_directory}/smtpd_scache
smtp_tls_security_level = may
smtp_tls_loglevel = 1
smtp_tls_session_cache_database = btree:${data_directory}/smtp_scache
# ==============================
# 制限設定
# ==============================
smtpd_recipient_restrictions =
permit_mynetworks,
permit_sasl_authenticated,
reject_unauth_destination,
reject_invalid_hostname,
reject_non_fqdn_hostname,
reject_non_fqdn_sender,
reject_non_fqdn_recipient,
reject_unknown_sender_domain,
reject_unknown_recipient_domain,
reject_rbl_client zen.spamhaus.org,
permit
smtpd_helo_required = yes
smtpd_helo_restrictions =
permit_mynetworks,
reject_non_fqdn_helo_hostname,
reject_invalid_helo_hostname,
permit
# ==============================
# パフォーマンス
# ==============================
default_process_limit = 100
smtpd_client_connection_rate_limit = 10
smtpd_client_message_rate_limit = 100
maximal_queue_lifetime = 5d
bounce_queue_lifetime = 5d
/etc/postfix/master.cf (Submission ポート設定):
# ==========================================================================
# service type private unpriv chroot wakeup maxproc command + args
# ==========================================================================
smtp inet n - n - - smtpd
submission inet n - n - - smtpd
-o syslog_name=postfix/submission
-o smtpd_tls_security_level=encrypt
-o smtpd_sasl_auth_enable=yes
-o smtpd_tls_auth_only=yes
-o smtpd_reject_unlisted_recipient=no
-o smtpd_recipient_restrictions=permit_sasl_authenticated,reject
-o milter_macro_daemon_name=ORIGINATING
smtps inet n - n - - smtpd
-o syslog_name=postfix/smtps
-o smtpd_tls_wrappermode=yes
-o smtpd_sasl_auth_enable=yes
-o smtpd_reject_unlisted_recipient=no
-o smtpd_recipient_restrictions=permit_sasl_authenticated,reject
-o milter_macro_daemon_name=ORIGINATING
設定の確認と反映:
# 設定の構文チェック
$ sudo postfix check
# (エラーがなければ何も出力されない)
# デフォルトと異なる設定値を表示
$ postconf -n
myhostname = mail.example.com
mydomain = example.com
myorigin = $mydomain
inet_interfaces = all
...
# 設定の反映 (再起動不要)
$ sudo postfix reload
postfix/postfix-script: refreshing the Postfix mail system
# Postfix の起動と自動起動
$ sudo systemctl enable --now postfix
3.3 仮想ドメインと仮想ユーザ
複数のドメインを 1 台のサーバでホスティングする場合に仮想ドメインを使用する。
/etc/postfix/main.cf (追加設定):
# 仮想メールボックスドメイン
virtual_mailbox_domains = hash:/etc/postfix/virtual_domains
virtual_mailbox_base = /var/mail/vhosts
virtual_mailbox_maps = hash:/etc/postfix/virtual_mailbox
virtual_alias_maps = hash:/etc/postfix/virtual_alias
virtual_minimum_uid = 1000
virtual_uid_maps = static:5000
virtual_gid_maps = static:5000
/etc/postfix/virtual_domains:
example.com OK
example.org OK
example.net OK
/etc/postfix/virtual_mailbox:
user1@example.com example.com/user1/Maildir/
user2@example.com example.com/user2/Maildir/
info@example.org example.org/info/Maildir/
admin@example.net example.net/admin/Maildir/
/etc/postfix/virtual_alias:
postmaster@example.com admin@example.com
abuse@example.com admin@example.com
sales@example.org user1@example.com, user2@example.com
# ハッシュ DB の作成
$ sudo postmap /etc/postfix/virtual_domains
$ sudo postmap /etc/postfix/virtual_mailbox
$ sudo postmap /etc/postfix/virtual_alias
# 仮想メールユーザの作成
$ sudo groupadd -g 5000 vmail
$ sudo useradd -g vmail -u 5000 -d /var/mail/vhosts -s /sbin/nologin vmail
$ sudo mkdir -p /var/mail/vhosts/{example.com,example.org,example.net}
$ sudo chown -R vmail:vmail /var/mail/vhosts
$ sudo postfix reload
3.4 トランスポートマップ
特定のドメイン宛メールの配送経路をカスタマイズする。
/etc/postfix/main.cf:
transport_maps = hash:/etc/postfix/transport
/etc/postfix/transport:
# 内部ドメインは特定サーバへ
internal.example.com smtp:[10.0.0.50]:25
# サブドメインはリレー経由
.partner.com relay:[relay.partner.com]:587
# 特定ドメインは破棄
blackhole.example.com discard:
# ローカル配送を強制
local.example.com local:
$ sudo postmap /etc/postfix/transport
$ sudo postfix reload
3.5 リレーホスト設定
すべての外部メールを特定のリレーサーバ経由で送信する場合の設定。
/etc/postfix/main.cf:
# すべての外部メールをリレー
relayhost = [smtp-relay.example.com]:587
# リレーホストへの SASL 認証
smtp_sasl_auth_enable = yes
smtp_sasl_password_maps = hash:/etc/postfix/sasl_passwd
smtp_sasl_security_options = noanonymous
smtp_tls_security_level = encrypt
/etc/postfix/sasl_passwd:
[smtp-relay.example.com]:587 relay_user:relay_password
$ sudo postmap /etc/postfix/sasl_passwd
$ sudo chmod 600 /etc/postfix/sasl_passwd /etc/postfix/sasl_passwd.db
$ sudo postfix reload
3.6 TLS/SSL 設定
Let's Encrypt 証明書の取得と設定:
# Certbot のインストールと証明書取得
$ sudo dnf install certbot
$ sudo certbot certonly --standalone -d mail.example.com
# 証明書ファイルの確認
$ sudo ls -la /etc/letsencrypt/live/mail.example.com/
total 4
lrwxrwxrwx 1 root root 40 Apr 1 10:00 cert.pem -> ../../archive/mail.example.com/cert1.pem
lrwxrwxrwx 1 root root 41 Apr 1 10:00 chain.pem -> ../../archive/mail.example.com/chain1.pem
lrwxrwxrwx 1 root root 45 Apr 1 10:00 fullchain.pem -> ../../archive/mail.example.com/fullchain1.pem
lrwxrwxrwx 1 root root 43 Apr 1 10:00 privkey.pem -> ../../archive/mail.example.com/privkey1.pem
/etc/postfix/main.cf (TLS 強化設定):
# 受信側 TLS
smtpd_tls_cert_file = /etc/letsencrypt/live/mail.example.com/fullchain.pem
smtpd_tls_key_file = /etc/letsencrypt/live/mail.example.com/privkey.pem
smtpd_tls_security_level = may
smtpd_tls_protocols = !SSLv2, !SSLv3, !TLSv1, !TLSv1.1
smtpd_tls_mandatory_protocols = !SSLv2, !SSLv3, !TLSv1, !TLSv1.1
smtpd_tls_mandatory_ciphers = high
smtpd_tls_exclude_ciphers = aNULL, eNULL, EXPORT, DES, RC4, MD5, PSK, aECDH, EDH-DSS-DES-CBC3-SHA, EDH-RSA-DES-CBC3-SHA, KRB5-DES, CBC3-SHA
smtpd_tls_dh1024_param_file = /etc/postfix/dh2048.pem
# 送信側 TLS
smtp_tls_security_level = may
smtp_tls_protocols = !SSLv2, !SSLv3, !TLSv1, !TLSv1.1
smtp_tls_mandatory_protocols = !SSLv2, !SSLv3, !TLSv1, !TLSv1.1
smtp_tls_mandatory_ciphers = high
# TLS セッションキャッシュ
smtpd_tls_session_cache_timeout = 3600s
# DH パラメータの生成 (時間がかかる)
$ sudo openssl dhparam -out /etc/postfix/dh2048.pem 2048
# TLS 接続のテスト
$ openssl s_client -connect mail.example.com:25 -starttls smtp
CONNECTED(00000003)
depth=2 O = Digital Signature Trust Co., CN = DST Root CA X3
...
SSL-Session:
Protocol : TLSv1.3
Cipher : TLS_AES_256_GCM_SHA384
...
3.7 スパムフィルタリングとアクセス制御
/etc/postfix/main.cf:
# Postscreen (ゾンビ/ボット対策)
postscreen_access_list = permit_mynetworks
postscreen_dnsbl_sites =
zen.spamhaus.org*2
bl.spamcop.net*1
b.barracudacentral.org*1
postscreen_dnsbl_threshold = 3
postscreen_greet_action = enforce
# ヘッダチェック
header_checks = regexp:/etc/postfix/header_checks
body_checks = regexp:/etc/postfix/body_checks
# Milter (SpamAssassin, OpenDKIM 連携)
milter_default_action = accept
milter_protocol = 6
smtpd_milters = unix:opendkim/opendkim.sock, unix:spamass/spamass.sock
non_smtpd_milters = unix:opendkim/opendkim.sock
/etc/postfix/header_checks:
/^Subject:.*viagra|cialis|lottery/i REJECT Spam content detected
/^From:.*@known-spam-domain\.com$/ REJECT Known spam domain
/^X-Mailer:.*mass.mailer/i REJECT Bulk mailer rejected
/etc/postfix/access (送信元制御):
# ドメイン単位の制御
example.com OK
spammer.com REJECT
192.168.1 OK
10.0.0.5 REJECT You are not allowed to send mail
# CIDR 形式
check_client_access cidr:/etc/postfix/client_access
4. Dovecot による受信サーバ構築
4.1 Dovecot アーキテクチャ
Dovecot は IMAP/POP3 サーバとして広く使用されており、高性能かつセキュアな設計が特徴である。
[MUA] --IMAP/POP3--> [Dovecot] ---> [メールボックス (Maildir/mbox)]
|
[認証バックエンド]
(PAM / LDAP / SQL / passwd)
# インストール
$ sudo dnf install dovecot # RHEL/Rocky/Alma
$ sudo apt install dovecot-imapd dovecot-pop3d # Debian/Ubuntu
4.2 IMAP/POP3 設定
/etc/dovecot/dovecot.conf:
# 有効にするプロトコル
protocols = imap pop3 lmtp
# リッスンするアドレス
listen = *, ::
/etc/dovecot/conf.d/10-master.conf:
service imap-login {
inet_listener imap {
port = 143
}
inet_listener imaps {
port = 993
ssl = yes
}
}
service pop3-login {
inet_listener pop3 {
port = 110
}
inet_listener pop3s {
port = 995
ssl = yes
}
}
service lmtp {
unix_listener /var/spool/postfix/private/dovecot-lmtp {
mode = 0600
user = postfix
group = postfix
}
}
# Postfix SASL 認証連携
service auth {
unix_listener /var/spool/postfix/private/auth {
mode = 0660
user = postfix
group = postfix
}
unix_listener auth-userdb {
mode = 0600
user = vmail
}
user = dovecot
}
service auth-worker {
user = vmail
}
4.3 メールボックス形式 (Maildir vs mbox)
| 項目 | Maildir | mbox |
|---|---|---|
| 構造 | 1メール1ファイル | 1ファイルに全メール |
| ロック | 不要 | 必要 |
| 破損リスク | 低い | 高い (ロック失敗時) |
| NFS 互換性 | 良好 | 問題あり |
| バックアップ | 差分が容易 | ファイル全体 |
| パフォーマンス | 大量メールに強い | 少数メールに有利 |
| ディスク使用量 | やや多い | 少ない |
| 推奨用途 | サーバ環境 | 小規模/レガシー |
/etc/dovecot/conf.d/10-mail.conf:
# Maildir 形式 (推奨)
mail_location = maildir:/var/mail/vhosts/%d/%n/Maildir
# mbox 形式の場合
# mail_location = mbox:~/mail:INBOX=/var/mail/%u
# メールボックスの自動作成
namespace inbox {
inbox = yes
mailbox Drafts {
auto = subscribe
special_use = \Drafts
}
mailbox Sent {
auto = subscribe
special_use = \Sent
}
mailbox "Sent Messages" {
special_use = \Sent
}
mailbox Trash {
auto = subscribe
special_use = \Trash
}
mailbox Junk {
auto = subscribe
special_use = \Junk
}
mailbox Archive {
auto = subscribe
special_use = \Archive
}
}
# メールプロセスのユーザ
mail_uid = vmail
mail_gid = vmail
mail_privileged_group = vmail
# メールボックスサイズの上限
mail_max_userip_connections = 20
Maildir ディレクトリ構造:
/var/mail/vhosts/example.com/user1/Maildir/
├── cur/ # 既読メール
├── new/ # 未読メール
├── tmp/ # 配送中の一時ファイル
├── .Drafts/
│ ├── cur/
│ ├── new/
│ └── tmp/
├── .Sent/
│ ├── cur/
│ ├── new/
│ └── tmp/
├── .Trash/
│ ├── cur/
│ ├── new/
│ └── tmp/
└── dovecot-uidlist
4.4 認証設定
/etc/dovecot/conf.d/10-auth.conf:
# 認証メカニズム
auth_mechanisms = plain login
# 平文認証は SSL 接続時のみ許可
disable_plaintext_auth = yes
# パスワードスキーム
# {SSHA512}, {BLF-CRYPT}, {SHA512-CRYPT} 等
auth_default_realm = example.com
# 認証バックエンド
!include auth-system.conf.ext
# !include auth-sql.conf.ext
# !include auth-ldap.conf.ext
# !include auth-passwdfile.conf.ext
/etc/dovecot/conf.d/auth-passwdfile.conf.ext (ファイルベース認証):
passdb {
driver = passwd-file
args = scheme=SHA512-CRYPT /etc/dovecot/users
}
userdb {
driver = passwd-file
args = /etc/dovecot/users
default_fields = uid=vmail gid=vmail home=/var/mail/vhosts/%d/%n
}
/etc/dovecot/users:
user1@example.com:{SHA512-CRYPT}$6$rounds=5000$salt$hashedpassword
user2@example.com:{SHA512-CRYPT}$6$rounds=5000$salt$hashedpassword
# パスワードハッシュの生成
$ doveadm pw -s SHA512-CRYPT
Enter new password:
Retype new password:
{SHA512-CRYPT}$6$rounds=656000$abc123...$xyz789...
/etc/dovecot/conf.d/auth-sql.conf.ext (SQL 認証):
passdb {
driver = sql
args = /etc/dovecot/dovecot-sql.conf.ext
}
userdb {
driver = sql
args = /etc/dovecot/dovecot-sql.conf.ext
}
/etc/dovecot/dovecot-sql.conf.ext:
driver = mysql
connect = host=localhost dbname=mailserver user=dovecot password=secret
default_pass_scheme = SHA512-CRYPT
password_query = SELECT email as user, password FROM virtual_users WHERE email='%u'
user_query = SELECT 5000 AS uid, 5000 AS gid, CONCAT('/var/mail/vhosts/', maildir) AS home FROM virtual_users WHERE email='%u'
4.5 SSL/TLS 設定
/etc/dovecot/conf.d/10-ssl.conf:
ssl = required
ssl_cert = </etc/letsencrypt/live/mail.example.com/fullchain.pem
ssl_key = </etc/letsencrypt/live/mail.example.com/privkey.pem
# 最小 TLS バージョン
ssl_min_protocol = TLSv1.2
# 暗号スイート
ssl_cipher_list = ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384
# DH パラメータ
ssl_dh = </etc/dovecot/dh.pem
# サーバ側の暗号優先
ssl_prefer_server_ciphers = yes
# DH パラメータ生成
$ sudo openssl dhparam -out /etc/dovecot/dh.pem 4096
# Dovecot の起動と自動起動
$ sudo systemctl enable --now dovecot
# SSL 接続のテスト
$ openssl s_client -connect mail.example.com:993
CONNECTED(00000003)
...
* OK [CAPABILITY IMAP4rev1 SASL-IR LOGIN-REFERRALS ID ENABLE IDLE ...] Dovecot ready.
5. メールキュー管理
5.1 mailq / postqueue
# キューの一覧表示
$ mailq
-Queue ID- --Size-- ----Arrival Time---- -Sender/Recipient-------
A1B2C3D4E5* 2048 Fri Apr 10 09:30:00 sender@example.com
recipient@example.org
B2C3D4E5F6 4096 Fri Apr 10 09:31:00 user@example.com
(connect to mx.example.net[203.0.113.10]:25: Connection timed out)
dest@example.net
C3D4E5F6G7! 1024 Fri Apr 10 09:32:00 admin@example.com
info@example.org
-- 3 Kbytes in 3 Requests.
キュー ID の記号の意味:
| 記号 | 意味 |
|---|---|
* | アクティブキュー (配送中) |
! | ホールドキュー (保留中) |
| なし | 遅延キュー (再試行待ち) |
# キューの統計表示
$ postqueue -p | tail -1
-- 156 Kbytes in 42 Requests.
# 特定キューの詳細表示
$ postcat -q A1B2C3D4E5
*** ENVELOPE RECORDS A1B2C3D4E5 ***
message_size: 2048 206 1
message_arrival_time: Fri Apr 10 09:30:00 2026
create_time: Fri Apr 10 09:30:00 2026
named_attribute: rewrite_context=local
sender: sender@example.com
recipient: recipient@example.org
*** MESSAGE CONTENTS A1B2C3D4E5 ***
...
# キュー内の全メールを即時再送
$ sudo postqueue -f
# 特定ドメイン宛のキューを即時再送
$ sudo postqueue -s example.org
5.2 postsuper によるキュー操作
# 特定メールの削除
$ sudo postsuper -d A1B2C3D4E5
postsuper: A1B2C3D4E5: removed
postsuper: Deleted: 1 message
# 全キューの削除 (注意して使用)
$ sudo postsuper -d ALL
postsuper: Deleted: 42 messages
# 遅延キューのみ削除
$ sudo postsuper -d ALL deferred
postsuper: Deleted: 30 messages
# メールをホールドキューに移動
$ sudo postsuper -h A1B2C3D4E5
postsuper: A1B2C3D4E5: placed on hold
postsuper: Held: 1 message
# ホールドキューから解放
$ sudo postsuper -H A1B2C3D4E5
postsuper: A1B2C3D4E5: released from hold
postsuper: Released: 1 message
# キューの再構築 (破損時)
$ sudo postsuper -r ALL
5.3 キュー監視とアラート
#!/bin/bash
# /usr/local/bin/check_mailqueue.sh
# メールキュー監視スクリプト
WARN_THRESHOLD=50
CRIT_THRESHOLD=200
QUEUE_COUNT=$(mailq | grep -c "^[A-F0-9]")
if [ "$QUEUE_COUNT" -ge "$CRIT_THRESHOLD" ]; then
echo "CRITICAL: Mail queue has $QUEUE_COUNT messages"
exit 2
elif [ "$QUEUE_COUNT" -ge "$WARN_THRESHOLD" ]; then
echo "WARNING: Mail queue has $QUEUE_COUNT messages"
exit 1
else
echo "OK: Mail queue has $QUEUE_COUNT messages"
exit 0
fi
# 遅延キューのドメイン別集計
$ mailq | grep -oP '(?<=@)[a-zA-Z0-9.-]+' | sort | uniq -c | sort -rn | head -10
15 problematic-domain.com
8 slow-server.org
5 example.net
3 mail.example.com
6. スパム対策
6.1 SpamAssassin
# インストール
$ sudo dnf install spamassassin
$ sudo systemctl enable --now spamassassin
/etc/mail/spamassassin/local.cf:
# スパム判定の閾値 (デフォルト: 5.0)
required_score 5.0
# スパムヘッダの書き換え
rewrite_header Subject [SPAM]
# レポート形式
report_safe 0
# Bayesian フィルタ
use_bayes 1
bayes_auto_learn 1
bayes_auto_learn_threshold_nonspam 0.1
bayes_auto_learn_threshold_spam 12.0
# ネットワークテスト
skip_rbl_checks 0
use_razor2 1
use_pyzor 1
# カスタムルール
score URIBL_BLACK 3.0
score RCVD_IN_SORBS_SPAM 2.0
# ホワイトリスト
whitelist_from *@trusted-partner.com
whitelist_from_rcvd *@example.com example.com
Postfix との連携 (spamass-milter):
$ sudo dnf install spamass-milter
/etc/sysconfig/spamass-milter:
EXTRA_FLAGS="-m -r 15"
/etc/postfix/main.cf に追加:
smtpd_milters = unix:spamass/spamass.sock
non_smtpd_milters = unix:spamass/spamass.sock
milter_default_action = accept
# SpamAssassin のテスト
$ spamassassin -t < /usr/share/doc/spamassassin/sample-spam.txt
...
Content analysis details: (1000.0 points, 5.0 required)
pts rule name description
---- ---------------------- --------------------------------------------------
1000 GTUBE BODY: Generic Test for Unsolicited Bulk Email
...
# Bayesian データベースの学習
$ sa-learn --spam /path/to/spam-folder/
Learned tokens from 150 message(s) (150 message(s) examined)
$ sa-learn --ham /path/to/ham-folder/
Learned tokens from 500 message(s) (500 message(s) examined)
# ルールの更新
$ sudo sa-update
6.2 OpenDKIM
# インストール
$ sudo dnf install opendkim opendkim-tools
/etc/opendkim.conf:
Mode sv
Syslog yes
SyslogSuccess yes
LogWhy yes
Canonicalization relaxed/simple
Domain example.com
Selector mail2026
KeyFile /etc/opendkim/keys/example.com/mail2026.private
Socket local:/var/spool/postfix/opendkim/opendkim.sock
PidFile /run/opendkim/opendkim.pid
OversignHeaders From
TrustAnchorFile /usr/share/dns/root.key
# 複数ドメイン対応
KeyTable refile:/etc/opendkim/KeyTable
SigningTable refile:/etc/opendkim/SigningTable
InternalHosts refile:/etc/opendkim/TrustedHosts
ExternalIgnoreList refile:/etc/opendkim/TrustedHosts
# DKIM 鍵の生成
$ sudo mkdir -p /etc/opendkim/keys/example.com
$ sudo opendkim-genkey -b 2048 -d example.com -D /etc/opendkim/keys/example.com -s mail2026 -v
opendkim-genkey: generating private key
opendkim-genkey: private key written to mail2026.private
opendkim-genkey: extracting public key
opendkim-genkey: DNS TXT record written to mail2026.txt
# 公開鍵の確認 (DNS に設定する内容)
$ cat /etc/opendkim/keys/example.com/mail2026.txt
mail2026._domainkey IN TXT ( "v=DKIM1; h=sha256; k=rsa; "
"p=MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA..." )
$ sudo chown -R opendkim:opendkim /etc/opendkim/keys/
/etc/opendkim/KeyTable:
mail2026._domainkey.example.com example.com:mail2026:/etc/opendkim/keys/example.com/mail2026.private
/etc/opendkim/SigningTable:
*@example.com mail2026._domainkey.example.com
/etc/opendkim/TrustedHosts:
127.0.0.1
::1
10.0.0.0/24
mail.example.com
example.com
/etc/postfix/main.cf に追加:
smtpd_milters = unix:opendkim/opendkim.sock
non_smtpd_milters = unix:opendkim/opendkim.sock
milter_default_action = accept
milter_protocol = 6
$ sudo systemctl enable --now opendkim
$ sudo postfix reload
# DKIM 署名の検証テスト
$ opendkim-testkey -d example.com -s mail2026 -vvv
opendkim-testkey: using default configfile /etc/opendkim.conf
opendkim-testkey: checking key 'mail2026._domainkey.example.com'
opendkim-testkey: key OK
6.3 Postscreen と Greylisting
/etc/postfix/master.cf (Postscreen 有効化):
# 標準の smtpd を Postscreen に置き換え
smtp inet n - n - 1 postscreen
smtpd pass - - n - - smtpd
dnsblog unix - - n - 0 dnsblog
tlsproxy unix - - n - 0 tlsproxy
/etc/postfix/main.cf (Postscreen 設定):
postscreen_access_list = permit_mynetworks, cidr:/etc/postfix/postscreen_access.cidr
postscreen_blacklist_action = drop
postscreen_greet_action = enforce
postscreen_dnsbl_action = enforce
postscreen_dnsbl_sites =
zen.spamhaus.org*2
bl.spamcop.net*1
b.barracudacentral.org*1
postscreen_dnsbl_threshold = 3
postscreen_dnsbl_whitelist_threshold = -1
postscreen_cache_map = btree:$data_directory/postscreen_cache
postscreen_greet_wait = ${stress?2}${stress:6}s
7. トラブルシューティング
ログの確認
# メールログの確認
$ sudo tail -f /var/log/maillog # RHEL 系
$ sudo tail -f /var/log/mail.log # Debian 系
$ sudo journalctl -u postfix -f # systemd
# 特定のメール ID を追跡
$ sudo grep "A1B2C3D4E5" /var/log/maillog
Apr 10 09:30:00 mail postfix/smtpd[12345]: A1B2C3D4E5: client=unknown[192.168.1.100]
Apr 10 09:30:00 mail postfix/cleanup[12346]: A1B2C3D4E5: message-id=<abc@example.com>
Apr 10 09:30:01 mail postfix/qmgr[12347]: A1B2C3D4E5: from=<sender@example.com>, size=2048, nrcpt=1 (queue active)
Apr 10 09:30:02 mail postfix/smtp[12348]: A1B2C3D4E5: to=<recipient@example.org>, relay=mx.example.org[203.0.113.20]:25, delay=2, delays=0.5/0.1/1/0.4, dsn=2.0.0, status=sent (250 2.0.0 Ok: queued)
Apr 10 09:30:02 mail postfix/qmgr[12347]: A1B2C3D4E5: removed
よくある問題と対処法
| 症状 | 原因 | 対処法 |
|---|---|---|
Connection timed out | ファイアウォール / ポートブロック | firewall-cmd --add-service=smtp |
Relay access denied | リレー設定不備 | mynetworks / SASL 認証の確認 |
Recipient address rejected | 宛先ドメイン未設定 | mydestination / virtual_mailbox_domains の確認 |
TLS handshake failed | 証明書の問題 | 証明書の期限・パスを確認 |
Authentication failed | 認証設定不備 | Dovecot 認証設定・SASL パスの確認 |
Mail loop detected | MX レコードがループ | DNS 設定の確認 |
Mailbox full | ディスク容量不足 | クォータ設定・ディスク空き容量の確認 |
Host or domain name not found | DNS 解決失敗 | /etc/resolv.conf・DNS サーバの確認 |
診断コマンド集
# Postfix の設定値を確認
$ postconf -d | grep mynetworks # デフォルト値
$ postconf -n | grep mynetworks # 変更された値
# SMTP 接続テスト
$ telnet mail.example.com 25
$ openssl s_client -connect mail.example.com:465
$ openssl s_client -connect mail.example.com:587 -starttls smtp
# メール配送テスト
$ echo "Test mail" | mail -s "Test Subject" user@example.com
# Dovecot の設定確認
$ doveconf -n
$ doveadm mailbox list -u user@example.com
INBOX
Drafts
Sent
Trash
Junk
Archive
# メール認証の検証
$ dig TXT example.com +short # SPF
$ dig TXT mail2026._domainkey.example.com +short # DKIM
$ dig TXT _dmarc.example.com +short # DMARC
# ポートの確認
$ ss -tlnp | grep -E '(25|110|143|465|587|993|995)'
LISTEN 0 100 *:25 *:* users:(("master",pid=1234,fd=13))
LISTEN 0 100 *:587 *:* users:(("master",pid=1234,fd=14))
LISTEN 0 100 *:993 *:* users:(("dovecot",pid=2345,fd=20))
LISTEN 0 100 *:995 *:* users:(("dovecot",pid=2345,fd=22))
# Postfix のプロセス状態
$ sudo postfix status
postfix/postfix-script: the Postfix mail system is running: PID: 1234
8. プロトコル・ポート比較表
| プロトコル | ポート | 暗号化 | 用途 |
|---|---|---|---|
| SMTP | 25 | STARTTLS (オプション) | MTA 間のメール転送 |
| SMTP Submission | 587 | STARTTLS (必須) | MUA からの送信 |
| SMTPS | 465 | 暗黙的 TLS | MUA からの送信 (レガシー/復活) |
| POP3 | 110 | STARTTLS (オプション) | メール受信 |
| POP3S | 995 | 暗黙的 TLS | メール受信 (暗号化) |
| IMAP | 143 | STARTTLS (オプション) | メール受信 |
| IMAPS | 993 | 暗黙的 TLS | メール受信 (暗号化) |
| LMTP | 24 | なし | ローカル配送 |
ファイアウォール設定:
# 必要なポートの開放
$ sudo firewall-cmd --permanent --add-service=smtp
$ sudo firewall-cmd --permanent --add-service=smtps
$ sudo firewall-cmd --permanent --add-port=587/tcp
$ sudo firewall-cmd --permanent --add-service=imaps
$ sudo firewall-cmd --permanent --add-service=pop3s
$ sudo firewall-cmd --reload
# 確認
$ sudo firewall-cmd --list-all
public (active)
services: smtp smtps imaps pop3s
ports: 587/tcp
9. ベストプラクティス
セキュリティ
- TLS を必須化する - Submission (587) と IMAP/POP3 への平文アクセスを禁止する
- TLSv1.2 以上を強制する - 古いプロトコルは無効化する
- SPF + DKIM + DMARC を全て設定する - 段階的にポリシーを強化する (none -> quarantine -> reject)
- Postscreen を有効化する - ボットからの接続を早期に遮断する
- Fail2ban を導入する - 認証失敗の繰り返しを検知しブロックする
- オープンリレーを絶対に許可しない -
mynetworksとsmtpd_recipient_restrictionsを適切に設定する
運用
- 証明書の自動更新 - certbot の cron/timer を設定する
- キュー監視 - 閾値ベースのアラートを設定する
- ログローテーション -
/var/log/maillogのローテーションを確認する - バックアップ - 設定ファイルとメールボックスの定期バックアップ
- DNS の冗長化 - MX レコードに複数のサーバを設定する (優先度を分ける)
- レート制限 - 送信レートを適切に制限し、ブラックリスト登録を防ぐ
パフォーマンス
- Maildir を使用する - mbox よりロック競合が少なく拡張性が高い
- 接続プール -
smtp_destination_concurrency_limitを調整する - DNS キャッシュ - ローカルに unbound 等のキャッシュ DNS を設置する
- メールボックスクォータ - ユーザごとのディスク使用量を制限する
監視項目
| 監視対象 | 閾値例 | ツール |
|---|---|---|
| メールキュー数 | Warning: 50, Critical: 200 | Nagios, Zabbix |
| ディスク使用率 | Warning: 80%, Critical: 95% | df, Prometheus |
| SMTP 応答時間 | Warning: 5s, Critical: 15s | check_smtp |
| 認証失敗回数 | 5回/分 以上 | Fail2ban, Prometheus |
| 送信メール数 | 異常増加を検知 | pflogsumm |
| TLS 証明書期限 | 30日前に警告 | check_ssl_cert |
10. 参考文献
- Postfix 公式ドキュメント
- Dovecot 公式ドキュメント
- SpamAssassin Wiki
- OpenDKIM
- RFC 5321 - SMTP
- RFC 7208 - SPF
- RFC 6376 - DKIM
- RFC 7489 - DMARC
- RFC 3501 - IMAP
- RFC 1939 - POP3
注記: 本ドキュメントは学習・参考目的で作成されたものであり、本番環境への適用時には各組織のセキュリティポリシーやネットワーク構成に合わせた調整が必要である。