In this article, we will show you how to set up and configure a mail server with Postfix, Dovecot, Spamassassin, SQLite and PostfixAdmin on an Ubuntu 16.04 VPS with Nginx and PHP 7.0. This guide should work on other Linux VPS systems as well but was tested and written for an Ubuntu 16.04 VPS. To set up a mail server with PostfixAdmin, just follow the steps below.
Table of Contents
1. Login to your VPS via SSH
ssh my_sudo_user@my_server
2. Update the system and install necessary packages
sudo apt-get update && sudo apt-get -y upgrade sudo apt-get -y install wget nano dbconfig-common sqlite3
3. Create a system user
For security reasons, we will create a new system user who will be the owner of all mailboxes.
sudo useradd -r -u 150 -g mail -d /var/vmail -s /sbin/nologin -c "Virtual Mail User" vmail sudo mkdir -p /var/vmail sudo chmod -R 770 /var/vmail sudo chown -R vmail:mail /var/vmail
4. Install PHP 7.0 and all required PHP modules
If you don’t have PHP installed on your server you can install the latest stable version of PHP 7.0 and all necessary modules, with the following command:
sudo apt-get -y install php-fpm php-cli php7.0-mbstring php7.0-imap php7.0-sqlite3
5. Install and configure Nginx
If you don’t have a web server installed on your machine, install Nginx from the official Ubuntu repositories:
sudo apt-get -y install nginx
Create a new Nginx server block with the following content:
sudo nano /etc/nginx/sites-available/postfixadmin.your_domain.com
server { listen 80; server_name postfixadmin.your_domain.com; return 301 https://$server_name$request_uri; } server { listen 443 ssl; server_name postfixadmin.your_domain.com; root /var/www/postfixadmin-3.0; index index.php; charset utf-8; ssl_certificate /etc/ssl/certs/ssl-cert-snakeoil.pem; ssl_certificate_key /etc/ssl/private/ssl-cert-snakeoil.key; ssl_protocols TLSv1.2; ssl_ciphers "EECDH+ECDSA+AESGCM:EECDH+aRSA+AESGCM:!aNULL:!eNULL:!LOW:!3DES:!MD5:!EXP:!PSK:!SRP:!DSS:!RC4"; ssl_prefer_server_ciphers on; ssl_session_cache shared:SSL:10m; ssl_session_timeout 10m; ssl_ecdh_curve secp521r1; location / { try_files $uri $uri/ index.php; } location ~* \.php$ { fastcgi_split_path_info ^(.+\.php)(/.+)$; include fastcgi_params; fastcgi_pass unix:/run/php/php7.0-fpm.sock; fastcgi_index index.php; include fastcgi_params; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; fastcgi_buffer_size 16k; fastcgi_buffers 4 16k; } }
Activate the server block by creating a symbolic link:
sudo ln -s /etc/nginx/sites-available/postfixadmin.your_domain.com /etc/nginx/sites-enabled/postfixadmin.your_domain.com
Test the Nginx configuration and restart nginx:
sudo nginx -t sudo service nginx restart
6. PostfixAdmin
PostfixAdmin is a PHP-based web frontend that allows you to manage the database that postfix uses for virtual domains and users. The latest version of PostfixAdmin, version 3, supports MySQL PostgreSQL and SQLite databases. In this guide, we will use the latter.
Download the PostfixAdmin archive from SourceForge and extract it in the /var/www/ directory:
wget -q -O - "http://downloads.sourceforge.net/project/postfixadmin/postfixadmin/postfixadmin-3.0/postfixadmin-3.0.tar.gz" | sudo tar -xzf - -C /var/www
Open the mail configuration file and edit the following values:
sudo nano /var/www/postfixadmin-3.0/config.inc.php
$CONF['configured'] = true; $CONF['database_type'] = 'sqlite'; $CONF['database_name'] = '/var/vmail/postfixadmin.db'; // $CONF['database_host'] = 'localhost'; // $CONF['database_user'] = 'postfix'; // $CONF['database_password'] = 'postfixadmin'; // $CONF['database_name'] = 'postfix'; $CONF['domain_path'] = 'NO'; $CONF['domain_in_mailbox'] = 'YES';
sudo chown -R www-data: /var/www/postfixadmin-3.0
Create the SQLite database:
sudo touch /var/vmail/postfixadmin.db sudo chown vmail:mail /var/vmail/postfixadmin.db sudo usermod -a -G mail www-data
To populate the database go to https://postfixadmin.your_domain.com/setup.php
and you should see something like below:
Testing database connection - OK - sqlite://:xxxxx@//var/vmail/postfixadmin.db
Create a new admin user:
bash /var/www/postfixadmin-3.0/scripts/postfixadmin-cli admin add admin@your_domain.com --password strong_password --password2 strong_password --superadmin 1 --active 1
7. Install and configure postfix
Install postfix with the command below:
sudo apt-get install postfix
Create the following files:
sudo nano /etc/postfix/sqlite_virtual_alias_maps.cf
dbpath = /var/vmail/postfixadmin.db query = SELECT goto FROM alias WHERE address='%s' AND active = '1'
sudo nano /etc/postfix/sqlite_virtual_alias_domain_maps.cf
dbpath = /var/vmail/postfixadmin.db query = SELECT goto FROM alias,alias_domain WHERE alias_domain.alias_domain = '%d' and alias.address = printf('%u', '@', alias_domain.target_domain) AND alias.active = 1 AND alias_domain.active='1'
sudo nano /etc/postfix/sqlite_virtual_alias_domain_catchall_maps.cf
dbpath = /var/vmail/postfixadmin.db query = SELECT goto FROM alias,alias_domain WHERE alias_domain.alias_domain = '%d' and alias.address = printf('@', alias_domain.target_domain) AND alias.active = 1 AND alias_domain.active='1'
sudo nano /etc/postfix/sqlite_virtual_domains_maps.cf
dbpath = /var/vmail/postfixadmin.db query = SELECT domain FROM domain WHERE domain='%s' AND active = '1'
sudo nano /etc/postfix/sqlite_virtual_mailbox_maps.cf
dbpath = /var/vmail/postfixadmin.db query = SELECT maildir FROM mailbox WHERE username='%s' AND active = '1'
sudo nano /etc/postfix/sqlite_virtual_alias_domain_mailbox_maps.cf
dbpath = /var/vmail/postfixadmin.db query = SELECT maildir FROM mailbox,alias_domain WHERE alias_domain.alias_domain = '%d' and mailbox.username = printf('%u', '@', alias_domain.target_domain) AND mailbox.active = 1 AND alias_domain.active='1'
Edit the main.cf
file:
postconf -e "myhostname = $(hostname -A)" postconf -e "virtual_mailbox_domains = sqlite:/etc/postfix/sqlite_virtual_domains_maps.cf" postconf -e "virtual_alias_maps = sqlite:/etc/postfix/sqlite_virtual_alias_maps.cf, sqlite:/etc/postfix/sqlite_virtual_alias_domain_maps.cf, sqlite:/etc/postfix/sqlite_virtual_alias_domain_catchall_maps.cf" postconf -e "virtual_mailbox_maps = sqlite:/etc/postfix/sqlite_virtual_mailbox_maps.cf, sqlite:/etc/postfix/sqlite_virtual_alias_domain_mailbox_maps.cf" postconf -e "smtpd_tls_cert_file = /etc/ssl/certs/ssl-cert-snakeoil.pem" postconf -e "smtpd_tls_key_file = /etc/ssl/private/ssl-cert-snakeoil.key" postconf -e "smtpd_use_tls = yes" postconf -e "smtpd_tls_auth_only = yes" postconf -e "smtpd_sasl_type = dovecot" postconf -e "smtpd_sasl_path = private/auth" postconf -e "smtpd_sasl_auth_enable = yes" postconf -e "smtpd_recipient_restrictions = permit_sasl_authenticated, permit_mynetworks, reject_unauth_destination" postconf -e "mydestination = localhost" postconf -e "mynetworks = 127.0.0.0/8" postconf -e "inet_protocols = ipv4" postconf -e "virtual_transport = lmtp:unix:private/dovecot-lmtp"
Open the master.cf
file, find submission inet n
and smtps inet n
sections and edit as follows:
sudo nano /etc/postfix/master.cf
smtp inet n - y - - smtpd #smtp inet n - y - 1 postscreen #smtpd pass - - y - - smtpd #dnsblog unix - - y - 0 dnsblog #tlsproxy unix - - y - 0 tlsproxy submission inet n - y - - smtpd -o syslog_name=postfix/submission -o smtpd_tls_security_level=encrypt -o smtpd_sasl_auth_enable=yes # -o smtpd_reject_unlisted_recipient=no -o smtpd_client_restrictions=permit_sasl_authenticated,reject # -o smtpd_helo_restrictions=$mua_helo_restrictions # -o smtpd_sender_restrictions=$mua_sender_restrictions # -o smtpd_recipient_restrictions= # -o smtpd_relay_restrictions=permit_sasl_authenticated,reject -o milter_macro_daemon_name=ORIGINATING smtps inet n - y - - smtpd -o syslog_name=postfix/smtps # -o smtpd_tls_wrappermode=yes -o smtpd_sasl_auth_enable=yes # -o smtpd_reject_unlisted_recipient=no -o smtpd_client_restrictions=permit_sasl_authenticated,reject # -o smtpd_helo_restrictions=$mua_helo_restrictions # -o smtpd_sender_restrictions=$mua_sender_restrictions # -o smtpd_recipient_restrictions= # -o smtpd_relay_restrictions=permit_sasl_authenticated,reject -o milter_macro_daemon_name=ORIGINATING
Enable and restart the postfix service
systemctl enable postfix systemctl restart postfix
8. Install and Configure Dovecot
Install dovecot with sqlite support using the command below:
sudo apt-get install dovecot-imapd dovecot-lmtpd dovecot-pop3d dovecot-sqlite
Open the /etc/dovecot/conf.d/10-mail.conf
file and change the following values:
mail_location = maildir:/var/vmail/%d/%n mail_privileged_group = mail mail_uid = vmail mail_gid = mail first_valid_uid = 150 last_valid_uid = 150
Open the /etc/dovecot/conf.d/10-auth.conf
file and change the following values:
auth_mechanisms = plain login #!include auth-system.conf.ext !include auth-sql.conf.ext
Create a new dovecot-sql.conf.ext
file:
sudo nano /etc/dovecot/dovecot-sql.conf.ext
driver = sqlite connect = /var/vmail/postfixadmin.db default_pass_scheme = MD5-CRYPT password_query = \ SELECT username as user, password, '/var/vmail/%d/%n' as userdb_home, \ 'maildir:/var/vmail/%d/%n' as userdb_mail, 150 as userdb_uid, 8 as userdb_gid \ FROM mailbox WHERE username = '%u' AND active = '1' user_query = \ SELECT '/var/vmail/%d/%n' as home, 'maildir:/var/vmail/%d/%n' as mail, \ 150 AS uid, 8 AS gid, printf('dirsize:storage=', quota) AS quota \ FROM mailbox WHERE username = '%u' AND active = '1'
In the /etc/dovecot/conf.d/10-ssl.conf
file enable SSL support:
ssl = yes
.
Open the /etc/dovecot/conf.d/15-lda.conf
file and set the postmaster_address
email address.
postmaster_address = postmaster@vps.your_domain.com
Open the /etc/dovecot/conf.d/10-master.conf
file, find the service lmtp section and change it to:
service lmtp { unix_listener /var/spool/postfix/private/dovecot-lmtp { mode = 0600 user = postfix group = postfix } }
find the service auth section and change it to:
service auth { unix_listener /var/spool/postfix/private/auth { mode = 0666 user = postfix group = postfix } unix_listener auth-userdb { mode = 0600 user = vmail #group = vmail } user = dovecot }
Change the service auth-worker section to the following:
service auth-worker { user = vmail }
Set the permissions:
chown -R vmail:dovecot /etc/dovecot chmod -R o-rwx /etc/dovecot
Enable and restart the dovecot service
systemctl enable dovecot systemctl restart dovecot
9. SpamAssassin
SpamAssassin is an open source tool written in Perl which helps filter out unwanted messages. If you want to enable and configure SpamAssassin please continue with the following steps.
To install SpamAssassin, run:
sudo apt-get install spamassassin sudo adduser spamd --disabled-login
Open the /etc/default/spamassassin
file and make the following changes:
ENABLED=1 OPTIONS="--create-prefs --max-children 5 -d 127.0.0.1 --username spamd --helper-home-dir /home/spamd/ -s /home/spamd/spamd.log" PIDFILE="/home/spamd/spamd.pid" CRON=1
To integrate SpamAssassin with Postfix, append the following at the end of the /etc/postfix/master.cf
file:
smtp inet n - - - - smtpd -o content_filter=spamassassin spamassassin unix - n n - - pipe user=nobody argv=/usr/bin/spamc -f -e /usr/sbin/sendmail -oi -f ${sender} ${recipient}
Enable and restart the SpamAssassin service
systemctl enable spamassassin systemctl restart spamassassin systemctl restart postfix
If everything is set up correctly now you should be able to login to your PostfixAdmin back-end by going to https://postfixadmin.your_domain.com/
and create your first virtual domain and mailbox.
Of course, you don’t have to set up and configure a mail server with PostfixAdmin yourself if you use one of our Mail Server Hosting services, in which case you can simply ask our expert Linux admins to set up and configure a mail server with PostfixAdmin for you. They are available 24×7 and will take care of your request immediately.
PS. If you liked this post on how to install postfixadmin, please share it with your friends on the social networks using the buttons on the left or simply leave a reply below. Thanks.
Your guide is missing SSL certificate configuration:
# nginx -t
nginx: [emerg] BIO_new_file(“/etc/ssl/certs/ssl-cert-snakeoil.pem”) failed (SSL: error:02001002:system library:fopen:No such file or directory:fopen(‘/etc/ssl/certs/ssl-cert-snakeoil.pem’,’r’) error:2006D080:BIO routines:BIO_new_file:no such file)
nginx: configuration file /etc/nginx/nginx.conf test failed
Do you have an SSL certificate installed on your server? Is it stored in /etc/ssl/certs/ssl-cert-snakeoil.pem file?
Hi,
I have configured postfix with backend MySQL and postfixadmin, server relay is working fine with all multiple virtual domains.. now I have an requirement for particular domain , where split delivery needs to be enabled to our old postfix server.. so that we can migrate it here easily.. could you please help me the configurations?
We do not know the configuration and the OS of your old Postfix server so we are not able to help you.
Your SSL settings will always break in Safari or Chrome etc:
ERR_SSL_VERSION_OR_CIPHER_MISMATCH
Look at the nginx server logs for errors, like a failure to load the certificates.
Also your postfixadmin setttings won’t work. I don’t have a solution.
Warning: config.local.php – NOT FOUND
It’s Recommended to store your own settings in config.local.php instead of editing config.inc.php
Create the file, and edit as appropriate (e.g. select database type etc)
Depends on: SQLite – OK
Error: Can’t connect to database
Please edit the $CONF[‘database_*’] parameters in config.local.php.
DEBUG INFORMATION
Connect: given database path does not exist, is not writable, or $CONF[‘database_name’] is empty.
Did you even test your tutorial?
Yes.
All our tutorials are tested and proven to work.
Hi, Thanks for the confirmation.
The postfixadmin issue was solved by setting the /var/mail directory to 777. sqlite3 needs write permission to both the directory and the file.
The SSL browser issues were solved by commenting out your ssl_ciphers in nginx site config. The restriction blocked Safari 11 and Chrome. Chrome and Safari blocked the SSL self-signed cert . Firefox was fine.
You enable SSL in dovecot but did not uncomment the certificates (snakeoil) nor did you create a certificate.
You installed Postfix but omitted the site config from the post-install scripts. Setting this to “no configuration” will break your guide.
Tested, and email does not work. Accounts cannot authenticate with Dovecot ( with/without SSL). No data is created in /var/vmail for any accounts.
Tested on Debian 9.1
This guide is written for Ubuntu 16.04. You may need to modify some steps if you are using Debian.
I never got this working on Debian 9.1 / openvz
Now working with a few tweaks except rspamd
Self-signed cert one liner:
openssl req -x509 -newkey rsa:4096 -keyout webmail.example.com-key.pem -out webmail.example.com-cert.pem -days 36500 -nodes -sha256 -subj “/C=BE/ST=LUIK/O=example/CN=webmail.example.com”
I cant login to backend.. It goes on loop if password is correct
Please check your mail server log files.
Works perfectly with Ubuntu server 16.04.
Thanks.
Hi,
On the first hand, thank you for your efforts helping us…
I am having troubles at the step of testing sqlite conection:
https://postfixadmin.your_domain.com/setup.php
I repeat all previous steps, and I only get 502 bad getaway, and seeing the log nginx only report:
connect() to unix:/run/php/php7.0-fpm.sock failed (2: No such file or directory)
Could you help me?
Best regards.
The PHP-FPM socket your are using doesn’t exist on your server. Make sure you are using the correct path to your PHP-FPM socket in your Nginx configuration.