Introduction

Postfix, Dovecot, Rspamd, DKIM & ARC — Done Right

Running your own mail server is still one of the most demanding infrastructure tasks. Modern mail delivery is no longer just SMTP — it is a trust pipeline involving SPF, DKIM, DMARC, ARC, reputation systems, content scanning, and strict authentication rules.

In this post we will walk through a clean, reproducible setup of:

  • Postfix – SMTP (inbound & outbound)
  • Dovecot – IMAP + SMTP authentication
  • Rspamd – spam filtering, DKIM & ARC signing
  • DKIM & ARC – cryptographic message authentication

All examples are based on Rocky Linux 10, with a focus on security, correctness, and debuggability.

⚠️ All passwords, secrets, and private data are replaced with placeholders such as
REPLACE_WITH_PASSWORD or example.com.


1. System Preparation

1.1 Base OS Setup

dnf update -y
dnf install -y epel-release

Ensure the system hostname is fully qualified:

hostnamectl set-hostname mail.example.com

Verify:

hostname -f

This must resolve via DNS to your public IP.


1.2 Required DNS Records (Before You Start)

At minimum:

mail.example.com.      A     <SERVER_IP>
example.com.          MX    10 mail.example.com.

Later we will add:

  • SPF
  • DKIM
  • DMARC
  • ARC (optional but recommended)

2. Installing Core Services

dnf install -y postfix dovecot dovecot-pigeonhole rspamd
systemctl enable postfix dovecot rspamd

Do not start them yet — configuration first.


3. Postfix Configuration

3.1 Main Configuration

/etc/postfix/main.cf (only relevant parts shown):

myhostname = mail.example.com
mydomain = example.com
myorigin = $mydomain

inet_interfaces = all
inet_protocols = ipv4

mydestination = localhost
relay_domains =

home_mailbox = Maildir/

smtpd_banner = $myhostname ESMTP

3.2 TLS Configuration

smtpd_tls_cert_file = /etc/ssl/certs/mail.pem
smtpd_tls_key_file  = /etc/ssl/private/mail.key

smtpd_tls_security_level = may
smtp_tls_security_level  = may

smtpd_tls_auth_only = yes

⚠️ Common error: wrong permissions on TLS keys
Ensure:

chmod 600 /etc/ssl/private/mail.key
chown root:root /etc/ssl/private/mail.key

3.3 SASL Authentication via Dovecot

smtpd_sasl_type = dovecot
smtpd_sasl_path = private/auth
smtpd_sasl_auth_enable = yes

smtpd_recipient_restrictions =
    permit_sasl_authenticated,
    permit_mynetworks,
    reject_unauth_destination

3.4 Rspamd Milter Integration

smtpd_milters = inet:127.0.0.1:11332
non_smtpd_milters = $smtpd_milters
milter_protocol = 6
milter_default_action = accept

4. Dovecot Configuration

4.1 Mail Location

/etc/dovecot/conf.d/10-mail.conf

mail_location = maildir:~/Maildir

4.2 Authentication

/etc/dovecot/conf.d/10-auth.conf

disable_plaintext_auth = yes
auth_mechanisms = plain login

4.3 Passdb / Userdb

For local users:

passdb {
  driver = pam
}

userdb {
  driver = passwd
}

4.4 Auth Socket for Postfix

/etc/dovecot/conf.d/10-master.conf

service auth {
  unix_listener /var/spool/postfix/private/auth {
    mode = 0660
    user = postfix
    group = postfix
  }
}

5. Rspamd Configuration

5.1 General Notes

Rspamd merges configuration from:

  1. /usr/share/rspamd/ (defaults)
  2. /etc/rspamd/override.d/ (replace)
  3. /etc/rspamd/local.d/ (extend/override)

Never re-declare module blocks in local.d.


6. DKIM Signing (Rspamd)

6.1 Generate DKIM Key

mkdir -p /var/lib/rspamd/dkim
rspamadm dkim_keygen \
  -d example.com \
  -s mail \
  -k /var/lib/rspamd/dkim/example.com.mail.key

Permissions:

chown _rspamd:_rspamd /var/lib/rspamd/dkim/example.com.mail.key
chmod 400 /var/lib/rspamd/dkim/example.com.mail.key

6.2 DKIM Configuration

/etc/rspamd/local.d/dkim_signing.conf

enabled = true;
selector = "mail";
sign_authenticated = true;
sign_local = true;

domain {
  example.com {
    path = "/var/lib/rspamd/dkim/example.com.mail.key";
    selector = "mail";
  }
}

Do NOT wrap this in dkim_signing {}
This is the #1 DKIM configuration error.


6.3 DNS DKIM Record

mail._domainkey.example.com TXT (
  "v=DKIM1; k=rsa; p=PUBLIC_KEY_HERE"
)

7. ARC Signing (Optional but Recommended)

7.1 Generate ARC Key

mkdir -p /var/lib/rspamd/arc
rspamadm dkim_keygen \
  -d example.com \
  -s arc \
  -k /var/lib/rspamd/arc/example.com.arc.key

7.2 ARC Configuration

/etc/rspamd/local.d/arc.conf

enabled = true;
domain = "example.com";
selector = "arc";
path = "/var/lib/rspamd/arc/example.com.arc.key";

⚠️ Missing ARC keys cause log warnings but do not break mail flow.


8. SPF & DMARC

8.1 SPF

example.com TXT "v=spf1 mx -all"

8.2 DMARC

_dmarc.example.com TXT (
  "v=DMARC1; p=quarantine; rua=mailto:dmarc@example.com; ruf=mailto:dmarc@example.com; fo=1"
)

9. Common Pitfalls (Learned the Hard Way)

❌ Nested DKIM configuration

Cause:

dkim_signing {
  dkim_signing {
  }
}

Fix:

  • Remove the outer block in local.d

❌ ARC enabled but no key

Symptom:

cannot read key from /var/lib/rspamd/arc/...

Fix:

  • Generate key or disable ARC explicitly

❌ TLS key unreadable by Postfix

Fix:

chmod 600

❌ Hostname not matching DNS

Fix:

  • Forward & reverse DNS must match

10. Testing & Validation

rspamadm configtest
systemctl start postfix dovecot rspamd

Send a test mail and verify headers:

DKIM-Signature: v=1; ...
ARC-Seal: i=1; ...
Authentication-Results: ...

External checks:

  • mail-tester.com
  • Gmail “Show original”

Final Summary

Setting up a modern, trustworthy mail server on Rocky Linux 10 is absolutely possible — but only if you treat it as a security system, not a legacy service.

With:

  • Postfix handling SMTP correctly
  • Dovecot providing secure authentication
  • Rspamd acting as the policy engine
  • DKIM and ARC cryptographically sealing your reputation

…you end up with a mail server that delivers reliably, passes modern validation, and behaves predictably under load.

Most failures are not software bugs — they are configuration layering mistakes. Once you understand how Postfix, Dovecot, and Rspamd merge responsibility, the entire system becomes surprisingly elegant.

Happy self-hosting ✉️

Views: 4

Building a Modern Mail Server on Rocky Linux 10

Johannes Rest


.NET Architekt und Entwickler


Beitragsnavigation


Schreibe einen Kommentar

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert