There is a new version of this tutorial available for Ubuntu 18.04 (Bionic Beaver).

Postfix Virtual Hosting With LDAP Backend With Dovecot As IMAP/POP3 Server On Ubuntu Hardy Heron 8.04 TLS - Page 2

Step 3: let's configure postfix

To use the dovecot sasl we need to add the following:

postconf -e "smtpd_sasl_type = dovecot"
postconf -e "smtpd_sasl_path = private/auth"

To enable dovecot deliver as default we need to add the following:

postconf -e "mailbox_transport = dovecot"
postconf -e "dovecot_destination_recipient_limit = 1"
postconf -e "mailbox_command = /usr/lib/dovecot/deliver"

Now we need to add the transports for dovecot deliver and gnarwl:

vi /etc/postfix/

Insert the following:

dovecot   unix  -       n       n       -       -       pipe
  flags=DRhu user=vmail:vmail argv=/usr/lib/dovecot/deliver -f ${sender} -d ${recipient)
gnarwl    unix  -       n       n       -       -       pipe
   flags=F  user=vmail argv=/usr/bin/gnarwl -a ${user}@${nexthop} -s ${sender}

To allow sasl authenticad users to send mail through postfix add the following to the entry smtpd_recipient_restrictions = permit_mynetworks

vi /etc/postfix/



Next we need to configure the ldap backend for postfix.

Insert the followong text at the end of the /etc/postfix/

Modify this to comply with your configuration (see assumptions).

ldap_bind_dn = cn=admin,dc=example,dc=tld
ldap_bind_pw = secret
ldap_search_base = o=hosting,dc=example,dc=tld
ldap_domain = dc=example,dc=tld
ldap_server_host = localhost
ldap_server_port = 389
ldap_version = 3

# aliases
aliases_server_host = $ldap_server_host
aliases_search_base = $ldap_search_base
aliases_query_filter = (&(&(objectClass=VirtualMailAlias)(mail=%s))(accountActive=TRUE))
aliases_result_attribute = maildrop
aliases_bind = yes
aliases_cache = no
aliases_bind_dn = $ldap_bind_dn
aliases_bind_pw = $ldap_bind_pw
aliases_version = $ldap_version

# VirtualForward
virtualforward_server_host = $ldap_server_host
virtualforward_search_base = $ldap_search_base
virtualforward_query_filter = (&(&(objectClass=VirtualMailAccount)(mail=%s))(vacationActive=FALSE)(forwardActive=TRUE)(accountActive=TRUE)(delete=FALSE))
virtualforward_result_attribute = maildrop
virtualforward_bind = yes
virtualforward_cache = no
virtualforward_bind_dn = $ldap_bind_dn
virtualforward_bind_pw = $ldap_bind_pw
virtualforward_version = $ldap_version

# Accounts
accounts_server_host = $ldap_server_host
accounts_search_base = $ldap_search_base
accounts_query_filter = (&(&(objectClass=VirtualMailAccount)(mail=%s))(forwardActive=FALSE)(accountActive=TRUE)(delete=FALSE))
accounts_result_attribute = mailbox
accounts_cache = no
accounts_bind = yes
accounts_bind_dn = $ldap_bind_dn
accounts_bind_pw = $ldap_bind_pw
accounts_version = $ldap_version
accountsmap_server_host = $ldap_server_host
accountsmap_search_base = $ldap_search_base
accountsmap_query_filter = (&(&(objectClass=VirtualMailAccount)(mail=%s))(forwardActive=FALSE)(accountActive=TRUE)(delete=FALSE))
accountsmap_result_attribute = mail
accountsmap_cache = no
accountsmap_bind = yes
accountsmap_bind_dn = $ldap_bind_dn
accountsmap_bind_pw = $ldap_bind_pw
accountsmap_version = $ldap_version

# virtual quota
quota_server_host = $ldap_server_host
quota_search_base = $ldap_search_base
quota_query_filter = (&(&(objectClass=VirtualMailAccount)(mail=%s))(accountActive=TRUE)(delete=FALSE))
quota_result_attribute = quota
quota_cache = no
quota_bind = yes
quota_bind_dn = $ldap_bind_dn
quota_bind_pw = $ldap_bind_pw
quota_version = $ldap_version

# Mail to reply for gnarwl and mail to forward during vacation
recipient_bcc_maps = ldap:vfm
vfm_server_host = $ldap_server_host
vfm_search_base = $ldap_search_base
vfm_query_filter = (&(&(objectClass=VirtualMailAccount)(mail=%s))(vacationActive=TRUE)(forwardActive=FALSE)(accountActive=TRUE)(delete=FALSE))
vfm_result_attribute = mailAutoreply
vfm_cache = no
vfm_bind = yes
vfm_bind_dn = $ldap_bind_dn
vfm_bind_pw = $ldap_bind_pw
vfm_version = $ldap_version

# transport_maps
maildrop_destination_concurrency_limit = 2
maildrop_destination_recipient_limit = 1
gnarwl_destination_concurrency_limit = 1
gnarwl_destination_recipient_limit = 1
transport_maps = hash:/etc/postfix/transport, ldap:transport
mydestination = $transport_maps, localhost, $myhostname, localhost.$mydomain, $mydomain
virtual_alias_maps = hash:/etc/postfix/virtual, ldap:virtualforward, ldap:aliases, ldap:accountsmap

# virtual accounts for delivery
virtual_mailbox_base = /home/vmail
virtual_mailbox_maps = ldap:accounts
virtual_minimum_uid = 1000
virtual_uid_maps = static:1000
virtual_gid_maps = static:1000

local_recipient_maps = proxy:unix:passwd.byname, $alias_maps, $virtual_mailbox_maps

Next we add the transport for gnarwl:

vi /etc/postfix/transport


.autoreply    :gnarwl

Compile the transport db:

postmap /etc/postfix/transport

This concludes the postfix configuration. We will restart the services later.

Share this page:

Suggested articles

3 Comment(s)

Add comment


By: Julio del Aguila

Take care with simbol ) replace it with } on the line:

flags=DRhu user=vmail:vmail argv=/usr/lib/dovecot/deliver -f ${sender} -d ${recipient)

replace to

flags=DRhu user=vmail:vmail argv=/usr/lib/dovecot/deliver -f ${sender} -d ${recipient}

You can save hours with this replace.


By: weec

need transport block

By: Julio del Aguila

If you have some problems with not receiver autoreply check transport in this tutorial and change the line

.autoreply    :gnarwl


.autoreply    gnarwl:


It works for me.