When implementing recipient whitelisting in Postfix, it's crucial to understand how different components interact. The smtpd_recipient_restrictions
parameter only applies to incoming SMTP connections, not messages injected via sendmail
or other local submission methods.
To enforce whitelisting for all outbound messages, including those sent via sendmail
, you need to modify main.cf
:
# Global restrictions for all messages
smtpd_recipient_restrictions =
reject_unauth_destination
check_recipient_access hash:/etc/postfix/whitelist
# Additional parameter for local submissions
smtpd_relay_restrictions =
permit_mynetworks
reject_unauth_destination
check_recipient_access hash:/etc/postfix/whitelist
# Critical for sendmail submissions
default_recipient_limit = 1
Your whitelist file should follow this format (e.g., /etc/postfix/whitelist
):
# Whitelisted domains (entire domain)
example.com OK
trusted.org OK
# Whitelisted individual addresses
admin@example.com OK
support@trusted.org OK
After editing, always remember to:
postmap /etc/postfix/whitelist
systemctl reload postfix
Verify your setup with these commands:
# Test via SMTP
telnet localhost 25
MAIL FROM: you@yourdomain.com
RCPT TO: blocked@external.com
# Test via sendmail
echo "Test" | sendmail -v blocked@external.com
Both methods should now reject non-whitelisted recipients with "554 5.7.1 Recipient address rejected: Access denied"
For more granular control, implement user-specific whitelists:
# In main.cf
smtpd_restriction_classes = user_whitelist
user_whitelist = check_sender_access hash:/etc/postfix/user_whitelists/${sender}, reject
# Then in master.cf
submission inet n - n - - smtpd
-o smtpd_restriction_classes=user_whitelist
-o smtpd_recipient_restrictions=permit_sasl_authenticated,reject_unauth_destination
Create individual whitelist files for each user in /etc/postfix/user_whitelists/
When dealing with large whitelists:
# Use indexed databases for better performance
whitelist_db_type = hash
# Cache lookups for better performance
smtpd_recipient_restrictions =
...
check_recipient_access proxy:btree:$data_directory/whitelist_cache
...
When configuring Postfix as a restricted mail gateway, many administrators discover that smtpd_recipient_restrictions
alone won't prevent outbound delivery to non-whitelisted addresses when using sendmail
or Postfix's sendmail compatibility interface. This occurs because these submission methods bypass SMTP-level restrictions.
To properly enforce recipient whitelisting, we need to implement restrictions at both the SMTP and submission levels:
# main.cf
smtpd_recipient_restrictions =
reject_unauth_destination
check_recipient_access hash:/etc/postfix/whitelist_recipients
smtpd_relay_restrictions =
permit_mynetworks
check_recipient_access hash:/etc/postfix/whitelist_recipients
reject
# Critical for sendmail interface
default_destination_recipient_limit = 1
Create your whitelist file (e.g., /etc/postfix/whitelist_recipients
) with format:
# Whitelist format
allowed@domain.com OK
@trusted-domain.com OK # Domain-wide permission
Then process it with:
postmap /etc/postfix/whitelist_recipients
systemctl reload postfix
For sendmail
submissions, add to master.cf
:
# Override default pickup service
pickup fifo n - n 60 1 pickup
-o content_filter=
-o receive_override_options=no_header_body_checks,no_unknown_recipient_checks
-o smtpd_restriction_classes=whitelist_only
-o smtpd_recipient_restrictions=check_recipient_access hash:/etc/postfix/whitelist_recipients,reject
Verify with these commands:
# Test SMTP restriction
telnet localhost 25
MAIL FROM:<test@example.com>
RCPT TO:<non-whitelisted@domain.com> # Should reject
# Test sendmail restriction
echo "Test" | sendmail -f test@example.com non-whitelisted@domain.com
For more granular control with LDAP or MySQL:
smtpd_recipient_restrictions =
reject_unauth_destination
check_client_access ldap:/etc/postfix/ldap-sender-groups.cf
check_recipient_access ldap:/etc/postfix/ldap-whitelist.cf
reject
Where ldap-whitelist.cf
contains your LDAP query logic for authorized recipients.