systemctl status postfix, and get a green active (exited). The ticket looks ready to close. On Debian and Ubuntu, though, that line tells you very little about whether mail is flowing. The unit you just checked is a wrapper. The process that actually listens on port 25 runs under a different unit, and that unit can be dead while the wrapper still looks fine.
This catches support staff at every level. The restart command returns cleanly, nothing red shows up on screen, and the customer is told mail is back. An hour later they report bounces or a queue that never drains. The rest of this guide is a short, repeatable way to check the real state before you say anything is fixed.
Why postfix.service exits right away
[email protected]. The text after the @ is the instance name. The default instance, the one almost every server runs, is named -, so its unit is [email protected].
On these distros, postfix.service is mostly a grouping unit. It typically has Type=oneshot, an ExecStart that runs /bin/true, and RemainAfterExit=yes. In plain terms, systemd runs a command that does nothing, sees it succeed, and marks the unit active from then on. That is what active (exited) means: the start command finished and the unit is considered up, but no long-running process belongs to it.
The real Postfix master daemon, which spawns smtpd, qmgr, and the rest, runs under [email protected]. Starting or restarting the wrapper pulls that instance along with it. If the instance fails, for example because of a syntax error in main.cf, a missing lookup table, or a port already in use, the wrapper usually stays active (exited). It has no process of its own to lose.
On RHEL-family systems, postfix.service usually runs the master process directly, so this split does not apply. The checks below still work. The instance-specific commands will just report that no such unit exists.
Check the instance unit, not the wrapper
BASH
# Show the wrapper unit file; look for ExecStart=/bin/true and RemainAfterExit=yes
systemctl cat postfix.service
# List every Postfix-related unit, including inactive and failed ones
systemctl list-units --all 'postfix*'
# Status of the default instance, where the master process actually runs
systemctl status [email protected]
# Script-friendly checks: each prints a single word such as active or failed
systemctl is-active [email protected]
systemctl is-failed [email protected]
# If more than one instance might exist, list them (needs root)
sudo postmulti -llist-units output is the fastest way to spot the problem. A healthy server shows postfix.service as active exited and [email protected] as active running. A broken one often shows the wrapper still active exited next to the instance as failed, or activating if it keeps crashing and restarting.
In the systemctl status [email protected] output, read the Active: line and the process tree under CGroup:. When Postfix is really up, you should see a master process and usually qmgr and pickup under it. An empty process tree, or an Active: line that says failed with a recent timestamp, means mail is down no matter what the wrapper says.
If you write a monitoring check or a post-restart script, point it at [email protected] with systemctl is-active. A check against postfix.service will report success even when the instance is dead.
Read why the instance stopped
BASH
# Recent log lines for the instance unit since the last boot
journalctl -u [email protected] -b --no-pager -n 50
# Postfix's own view of whether the master process is running
sudo postfix status
# Check config files, permissions, and ownership without starting anything
sudo postfix checkpostfix/master or postfix/postfix-script that start with fatal: or error:. Common causes include an unreadable or missing .db lookup file that was never rebuilt with postmap, a typo in a main.cf parameter, bind: Address already in use when another MTA such as Exim or Sendmail still holds port 25, or permission problems under /var/spool/postfix.
postfix status asks Postfix directly whether its master process is alive, so it does not depend on how systemd labels anything. postfix check validates the config and file permissions. It is a good first step after any edit and is safe to run on a live server.
On some Debian and Ubuntu setups, Postfix also logs through rsyslog to /var/log/mail.log. If the journal looks thin, check that file for the same fatal: lines. Where logs go depends on the release and how logging was configured, so verify on your own server rather than assuming.
Confirm something is actually listening on port 25
smtp service might be commented out in master.cf, or inet_interfaces might be set so Postfix listens only on loopback. So check the socket itself.
BASH
# Listening TCP sockets on port 25 and the owning process (-p needs root)
sudo ss -ltnp 'sport = :25'
# Submission ports, if this server accepts authenticated clients
sudo ss -ltnp '( sport = :587 or sport = :465 )'
# Which interfaces and protocols Postfix is configured to bind (read-only)
postconf inet_interfaces inet_protocolsLISTEN line with a local address of 0.0.0.0:25, [::]:25, or the server's public IP, and a process name of master. There are a few other patterns to recognize:
- No output at all: nothing is listening. If the instance unit shows as running, look at
master.cf. - Only
127.0.0.1:25or[::1]:25: Postfix is listening on loopback only. Local scripts can send mail, but nothing from outside can connect. Compare this with theinet_interfacesvalue. - A process other than
masteron port 25: another mail server is holding the port. This often explains abinderror in the journal.
ss check only proves the socket exists on this host. A firewall, a security group, or a provider-level block on port 25 can still stop outside connections. For the last check, connect from a different machine with a plain TCP client such as nc or telnet and confirm you get a 220 SMTP greeting. The exact client and flags vary by distro, so use whatever is installed. If the banner appears locally but not remotely, the problem is no longer Postfix.
What to check before closing the ticket
postfix.service on Debian or Ubuntu. Before you tell anyone mail is working, confirm three separate things: [email protected] is active (running) with a master process in its tree, the journal for that instance shows no fresh fatal: lines, and ss shows master listening on port 25 on the address you expect. If any of those is missing, the restart did not fix anything. It just hid the failure behind a wrapper that has nothing to fail. Teach junior staff to run these checks as one habit after every Postfix restart, and point monitoring at the instance and the socket instead of the wrapper.