Security

Configure Let’s Encrypt SSL for iRedMail Server

iRedMail generates a self-signed SSL certificate during installation. Browsers and email clients distrust it, which means warning messages for webmail users and potential delivery issues with strict receiving servers. Replacing it with a Let’s Encrypt certificate fixes both problems and takes about five minutes.

Original content from computingforgeeks.com - post 36364

Tested March 2026 | iRedMail 1.7.4 on Ubuntu 24.04, Debian 12, Rocky Linux 10. Certbot 2.x with HTTP-01 challenge.

This guide assumes you already have iRedMail installed and running. If not, start with the installation guide for your OS: Ubuntu 24.04/22.04, Debian 12, or Rocky Linux / AlmaLinux.

Prerequisites

  • A working iRedMail server with Nginx
  • A DNS A record for your mail hostname (e.g., mail.example.com) pointing to the server IP
  • Port 80 open and reachable from the internet (required for the HTTP-01 challenge)
  • Root or sudo access

Install Certbot

On Ubuntu and Debian:

sudo apt install -y certbot

On Rocky Linux and AlmaLinux:

sudo dnf install -y certbot

Obtain the Certificate

Certbot needs port 80 to complete the HTTP-01 challenge. Since Nginx occupies that port, stop it temporarily:

sudo systemctl stop nginx

Request the certificate:

sudo certbot certonly --standalone -d mail.example.com --non-interactive --agree-tos -m [email protected]

On success, certbot stores the certificate files at:

/etc/letsencrypt/live/mail.example.com/fullchain.pem
/etc/letsencrypt/live/mail.example.com/privkey.pem

Replace the Self-Signed Certificate

iRedMail’s Nginx, Postfix, and Dovecot configurations all reference two certificate paths. On Debian and Ubuntu these are /etc/ssl/certs/iRedMail.crt and /etc/ssl/private/iRedMail.key. On RHEL-based systems (Rocky, AlmaLinux) they are /etc/pki/tls/certs/iRedMail.crt and /etc/pki/tls/private/iRedMail.key.

Back up the originals first, then create symlinks to the Let’s Encrypt files.

Debian / Ubuntu

sudo mv /etc/ssl/certs/iRedMail.crt /etc/ssl/certs/iRedMail.crt.bak
sudo mv /etc/ssl/private/iRedMail.key /etc/ssl/private/iRedMail.key.bak
sudo ln -s /etc/letsencrypt/live/mail.example.com/fullchain.pem /etc/ssl/certs/iRedMail.crt
sudo ln -s /etc/letsencrypt/live/mail.example.com/privkey.pem /etc/ssl/private/iRedMail.key

Rocky Linux / AlmaLinux

sudo mv /etc/pki/tls/certs/iRedMail.crt /etc/pki/tls/certs/iRedMail.crt.bak
sudo mv /etc/pki/tls/private/iRedMail.key /etc/pki/tls/private/iRedMail.key.bak
sudo ln -s /etc/letsencrypt/live/mail.example.com/fullchain.pem /etc/pki/tls/certs/iRedMail.crt
sudo ln -s /etc/letsencrypt/live/mail.example.com/privkey.pem /etc/pki/tls/private/iRedMail.key

The symlink approach means all three services (Nginx, Postfix, Dovecot) pick up the Let’s Encrypt certificate without editing any config files. When certbot renews the certificate, the symlinks automatically point to the new files.

Restart Services

Restart Nginx, Postfix, and Dovecot to load the new certificate:

sudo systemctl restart nginx postfix dovecot

There is no need to reboot the server. Restarting these three services is sufficient.

Verify the Certificate

Check that Nginx serves the Let’s Encrypt certificate:

echo | openssl s_client -connect mail.example.com:443 -servername mail.example.com 2>/dev/null | openssl x509 -noout -issuer -dates

The output should show Let’s Encrypt as the issuer:

issuer=C=US, O=Let's Encrypt, CN=R11
notBefore=Mar 27 19:34:10 2026 GMT
notAfter=Jun 25 19:34:09 2026 GMT

Verify Postfix SMTP is also using the new certificate on port 587:

echo | openssl s_client -connect mail.example.com:587 -starttls smtp 2>/dev/null | openssl x509 -noout -issuer

And Dovecot IMAPS on port 993:

echo | openssl s_client -connect mail.example.com:993 2>/dev/null | openssl x509 -noout -issuer

All three should show the same Let’s Encrypt issuer. If any still shows the self-signed certificate (issuer contains “iRedMail”), the symlink for that service didn’t take effect. Double-check the paths and restart the service again.

Configure Automatic Renewal

Let’s Encrypt certificates expire every 90 days. Certbot installs a systemd timer (or cron job) that handles renewal automatically. Verify it’s active:

sudo certbot renew --dry-run

The dry run should complete without errors.

One problem: Nginx holds port 80, so the standalone renewal will fail unless Nginx is stopped first. Configure certbot to stop Nginx before renewal and restart all mail services after:

sudo tee /etc/letsencrypt/renewal-hooks/pre/stop-nginx.sh > /dev/null << 'EOF'
#!/bin/bash
systemctl stop nginx
EOF

sudo tee /etc/letsencrypt/renewal-hooks/post/restart-services.sh > /dev/null << 'EOF'
#!/bin/bash
systemctl restart nginx postfix dovecot
EOF

sudo chmod +x /etc/letsencrypt/renewal-hooks/pre/stop-nginx.sh
sudo chmod +x /etc/letsencrypt/renewal-hooks/post/restart-services.sh

This ensures Nginx releases port 80 for the challenge, and all three TLS-dependent services restart with the fresh certificate after renewal. Test the full renewal flow:

sudo certbot renew --dry-run

Troubleshooting

Error: "Problem binding to port 80"

Certbot in standalone mode needs port 80 free. Confirm Nginx is stopped before running certbot:

sudo systemctl stop nginx
sudo ss -tlnp | grep :80

If something else is on port 80 (Apache, another process), stop it first.

Error: "DNS problem: NXDOMAIN looking up A for mail.example.com"

The A record for your mail hostname doesn't exist or hasn't propagated. Verify with:

dig +short mail.example.com A

This must return your server's public IP. If it's empty, add the A record in your DNS provider and wait for propagation (usually under 5 minutes with Cloudflare).

Postfix still using the old certificate after restart

Verify the symlink points to the right file:

ls -la /etc/ssl/certs/iRedMail.crt

It should point to /etc/letsencrypt/live/mail.example.com/fullchain.pem. If the symlink is broken (shows red in ls), the Let's Encrypt directory might have different permissions. Fix with:

sudo chmod 755 /etc/letsencrypt/live/ /etc/letsencrypt/archive/

SELinux blocking certbot on Rocky Linux

If certbot fails on Rocky Linux or AlmaLinux with a permission denied error, check for SELinux denials:

sudo ausearch -m avc -ts recent | grep certbot

If there are denials, restore the correct file contexts on the Let's Encrypt directory:

sudo restorecon -Rv /etc/letsencrypt/

For managing mail domains and users after securing the server, see the iRedMail domain and user management guide.

Related Articles

Email Install Postal Mail Server on Ubuntu 22.04|20.04|18.04 Automation Manage Users and Groups in FreeIPA using CLI Security AdBlock360 – More than an adblocker: Comprehensive Online Protection and Enhanced Browsing Debian How To Install Suricata on Debian 11/Debian 10

7 thoughts on “Configure Let’s Encrypt SSL for iRedMail Server”

  1. My current iRedmail server is behind a reverse proxy (Nginx Proxy Manager) to expose the web interface at 443. Unfortunately it’s still using the self signed cert for ports 587 and 25 so some self-hosted services like Peertube and Nextcloud will not allow me to use my iRm email credentials for those configs because “warning – self signed cert” errors. How would I resolve this?

    Reply

Leave a Comment

Press ESC to close