Help


Documentation & Tutorials

Setup a mail server on Ubuntu Bionic Beaver (18.04)

Overview - Configure a secure mail server

In this tutorial you will learn how to configure a mail server that uses DKIM, Rspamd and MariaDB to deliver mails securely. You will install a Roundcube webmail interface to be able to read your mails directly from your browser.

This guide consists of several steps:

Pre-work

Before you continue with this tutorial, some pre-work is required to make sure your mail server will be working.

  • To ensure that other servers will accept mails sent from your instance a valid reverse DNS within your own domain name (for example mail.domain.com) must be configured.
  • The SMTP ports have been unlocked in the security group of the server.

1 . Start by updating your system to make sure you have the latest software releases installed:

apt-get update && apt-get upgrade

2 . Before starting the installation of the mail server, make sure that there is no other mail software already installed:

service sendmail stop; update-rc.d -f sendmail remove

Note: If you receive a message Failed to stop sendmail.service: Unit sendmail.service not loaded. you can ignore it. It will only tell you that sendmail has not been installed, so it can’t be removed.

Installing PostfixAdmin

All mailboxes will belong to virtual users, to manage them we need one system user which will be the owner of all mailboxes and will be used by all virtual users to access email on the server. The home directory of the user will be /var/mail/vmail and all mailboxes will be stored in that directory:

sudo groupadd -g 5000 vmail
sudo useradd -u 5000 -g vmail -s /usr/sbin/nologin -d /var/mail/vmail -m vmail

As PostfixAdmin is a PHP application, a webserver is required. We will use Nginx with PHP7.2 and MariaDB:

sudo apt-get install nginx mariadb-server php7.2-fpm php7.2-cli php7.2-imap php7.2-json php7.2-mysql php7.2-opcache php7.2-mbstring php7.2-readline

1 . Set a root password for MariaDB:

mysql_secure_installation

The setup tool will ask you a few questions:

  • Enter current password for root (enter for none): Press Enter
  • Set root password? [Y/n] Type Y
  • New password: Enter the password for the root user
  • Re-enter new password: Repeat the password
  • Remove anonymous users? [Y/n] Type Y
  • Disallow root login remotely? [Y/n] Type Y
  • Remove test database and access to it? [Y/n] Type Y
  • Reload privilege tables now? [Y/n] Type Y

2 . Download and unpack PostfixAdmin. The latest version at the time of writing of this tutorial is version 3.2:

wget https://downloads.sourceforge.net/project/postfixadmin/postfixadmin/postfixadmin-3.2/postfixadmin-3.2.tar.gz
tar xzf postfixadmin-3.2.tar.gz

3 . Move PostfixAdmin into the directory /var/www/postfixadmin:

sudo mv postfixadmin-3.2/ /var/www/postfixadmin
rm -f postfixadmin-3.2.tar.gz
mkdir /var/www/postfixadmin/templates_c

4 . Change the ownership of the directory to the www-data user, as Nginx and PHP are using it:

sudo chown -R www-data: /var/www/postfixadmin

5 . PostfixAdmin will use a MySQL database to store information. Connect to your MariaDB Server to create a new database and user:

mysql -u root -p

6 . Create the database, remember to replace your_secret_password with a password for the postfixadmin user:

CREATE DATABASE postfixadmin;
GRANT ALL ON postfixadmin.* TO 'postfixadmin'@'localhost' IDENTIFIED BY 'your_secret_password';
FLUSH PRIVILEGES;

7 . Create a configuration file /var/www/postfixadmin/config.local.php and open it in a text browser:

<?php
$CONF['configured'] = true;

$CONF['database_type'] = 'mysqli';
$CONF['database_host'] = 'localhost';
$CONF['database_user'] = 'postfixadmin';
$CONF['database_password'] = 'your_secret_password';
$CONF['database_name'] = 'postfixadmin';

$CONF['default_aliases'] = array (
  'abuse'      => 'abuse@example.com',
  'hostmaster' => 'hostmaster@example.com',
  'postmaster' => 'postmaster@example.com',
  'webmaster'  => 'webmaster@example.com'
);

$CONF['fetchmail'] = 'NO';
$CONF['show_footer_text'] = 'NO';

$CONF['quota'] = 'YES';
$CONF['domain_quota'] = 'YES';
$CONF['quota_multiplier'] = '1024000';
$CONF['used_quotas'] = 'YES';
$CONF['new_quota_table'] = 'YES';

$CONF['aliases'] = '0';
$CONF['mailboxes'] = '0';
$CONF['maxquota'] = '0';
$CONF['domain_quota_default'] = '0';
?>

Remember to replace your_secret_password with the password for the database user.

The configuration defines the database type, login credentials, default aliases, disabled fetchmail and enabled quota.

8 . Now run the following script to install the database schema:

sudo -u www-data php /var/www/postfixadmin/public/upgrade.php

As the database is ready now, it is possible to create the first superadmin from the CLI tools:

sudo bash /var/www/postfixadmin/scripts/postfixadmin-cli admin add

9 . Enter the email address of the admin, and answer the questions of the CLI.

To secure the communication with the webserver, we use Let’s Encrypt to get a free SSL certificate:

sudo apt-get install software-properties-common lsb-release
sudo add-apt-repository ppa:certbot/certbot
sudo apt-get update
sudo install python-certbot-nginx
sudo certbot --nginx

Certbot will automatically request the certificate and rewrite the Nginx configuration file. The file /etc/nginx/sites-enabled/mail.example.com.conf should look as the following example:

server {
    if ($host = mail.example.com) {
        return 301 https://$host$request_uri;
    } # managed by Certbot
    listen 80;
    server_name mail.example.com;
}

server {
    listen 443 ssl http2;
    server_name mail.example.com;
    root /var/www;

    location / {
       try_files $uri $uri/ /index.php;
    }

    location /postfixadmin {
       index index.php;
       try_files $uri $uri/ /postfixadmin/public/login.php;
    }

    location ~* \.php$ {
         fastcgi_split_path_info ^(.+?\.php)(/.*)$;
         if (!-f $document_root$fastcgi_script_name) {return 404;}
         fastcgi_pass  unix:/run/php/php7.2-fpm.sock;
         fastcgi_index index.php;
         include fastcgi_params;
         fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
    }

    ssl_certificate /etc/letsencrypt/live/mail.example.com/fullchain.pem; # managed by Certbot
    ssl_certificate_key /etc/letsencrypt/live/mail.example.com/privkey.pem; # managed by Certbot
}

10 . Restart Nginx to activate the configuration:

service nginx restart

Installation of Postfix and Dovecot

1 . Install the required software. You can install all required packages with one command with apt-get:

sudo apt-get install postfix postfix-mysql dovecot-imapd dovecot-lmtpd dovecot-pop3d dovecot-mysql

You will be asked some questions during the installation:

  • For server type choose Internet Site
  • For mail name, enter the FQDN of the server (for example: mail.example.com)

We use virtual users in our configuration. Therefore we have to create the configuration files for postfix to use the database we have created previously.

2 . Start by creating a directory to store the files:

sudo mkdir -p /etc/postfix/sql

3 . Create and open the file /etc/postfix/sql/mysql_virtual_domains_maps.cf in a text editor and put the following content in it:

user = postfixadmin
password = your_secret_password
hosts = 127.0.0.1
dbname = postfixadmin
query = SELECT domain FROM domain WHERE domain='%s' AND active = '1'

4 . Create and open the file /etc/postfix/sql/mysql_virtual_alias_maps.cf in a text editor and put the following content in it:

user = postfixadmin
password = your_secret_password
hosts = 127.0.0.1
dbname = postfixadmin
query = SELECT goto FROM alias WHERE address='%s' AND active = '1'

5 . Create and open the file /etc/postfix/sql/mysql_virtual_alias_domain_catchall_maps.cf in a text editor and put the following content in it:

user = postfixadmin
password = your_secret_password
hosts = 127.0.0.1
dbname = postfixadmin
query  = SELECT goto FROM alias,alias_domain WHERE alias_domain.alias_domain = '%d' and alias.address = CONCAT('@', alias_domain.target_domain) AND alias.active = 1 AND alias_domain.active='1'

6 . Create and open the file /etc/postfix/sql/mysql_virtual_alias_domain_maps.cf in a text editor and put the following content in it:

user = postfixadmin
password = your_secret_password
hosts = 127.0.0.1
dbname = postfixadmin
query = SELECT goto FROM alias,alias_domain WHERE alias_domain.alias_domain = '%d' and alias.address = CONCAT('%u', '@', alias_domain.target_domain) AND alias.active = 1 AND alias_domain.active='1'

7 . Create and open the file /etc/postfix/sql/mysql_virtual_mailbox_maps.cf in a text editor and put the following content in it:

user = postfixadmin
password = your_secret_password
hosts = 127.0.0.1
dbname = postfixadmin
query = SELECT maildir FROM mailbox WHERE username='%s' AND active = '1'

8 . Create and open the file /etc/postfix/sql/mysql_virtual_alias_domain_mailbox_maps.cf in a text editor and put the following content in it:

user = postfixadmin
password = your_secret_password
hosts = 127.0.0.1
dbname = postfixadmin
query = SELECT maildir FROM mailbox,alias_domain WHERE alias_domain.alias_domain = '%d' and mailbox.username = CONCAT('%u', '@', alias_domain.target_domain) AND mailbox.active = 1 AND alias_domain.active='1'

9 . Once the MySQL configuration files are created, update the configuration of Postfix:

sudo postconf -e "virtual_mailbox_domains = mysql:/etc/postfix/sql/mysql_virtual_domains_maps.cf"
sudo postconf -e "virtual_alias_maps = mysql:/etc/postfix/sql/mysql_virtual_alias_maps.cf, mysql:/etc/postfix/sql/mysql_virtual_alias_domain_maps.cf, mysql:/etc/postfix/sql/mysql_virtual_alias_domain_catchall_maps.cf"
sudo postconf -e "virtual_mailbox_maps = mysql:/etc/postfix/sql/mysql_virtual_mailbox_maps.cf, mysql:/etc/postfix/sql/mysql_virtual_alias_domain_mailbox_maps.cf"

Note: The postconf command can be used to display the actual configuration, change configuration values, or display other configuration information about the Postfix mail system.

Local delivery will be handled by Dovecot’s local delivery agent. It will take mail from a MTA (Postfix) and deliver it to a local user’s mailbox.

sudo postconf -e "virtual_transport = lmtp:unix:private/dovecot-lmtp"

10 . Configure the TLS parameters by using the Let’s encrypt SSL certificate:

sudo postconf -e 'smtp_tls_security_level = may'
sudo postconf -e 'smtpd_tls_security_level = may'
sudo postconf -e 'smtp_tls_note_starttls_offer = yes'
sudo postconf -e 'smtpd_tls_loglevel = 1'
sudo postconf -e 'smtpd_tls_received_header = yes'
sudo postconf -e 'smtpd_tls_cert_file = /etc/letsencrypt/live/mail.example.com/fullchain.pem'
sudo postconf -e 'smtpd_tls_key_file = /etc/letsencrypt/live/mail.example.com/privkey.pem'

11 . Configure the authenticated SMTP settings:

sudo postconf -e 'smtpd_sasl_type = dovecot'
sudo postconf -e 'smtpd_sasl_path = private/auth'
sudo postconf -e 'smtpd_sasl_local_domain ='
sudo postconf -e 'smtpd_sasl_security_options = noanonymous'
sudo postconf -e 'broken_sasl_auth_clients = yes'
sudo postconf -e 'smtpd_sasl_auth_enable = yes'
sudo postconf -e 'smtpd_recipient_restrictions = permit_sasl_authenticated,permit_mynetworks,reject_unauth_destination'

12 . Enable the the TLS/SSL and submission ports in the Postfix configuration file. Open the file /etc/postfix/master.cf with a text editor, uncomment the submission and smtps sections as following. Make sure that there is a whitespace in front of the -o as it is required:

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

13 . Restart postfix to take the modifications into effect:

service postfix restart

14 . Edit the file /etc/dovecot/dovecot-sql.conf.ext as following:

driver = mysql
connect = host=127.0.0.1 dbname=postfixadmin user=postfixadmin password=your_secret_password
default_pass_scheme = MD5-CRYPT
iterate_query = SELECT username AS user FROM mailbox
user_query = SELECT CONCAT('/var/mail/vmail/',maildir) AS home, \
  CONCAT('maildir:/var/mail/vmail/',maildir) AS mail, \
  5000 AS uid, 5000 AS gid, CONCAT('*:bytes=',quota) AS quota_rule \
  FROM mailbox WHERE username = '%u' AND active = 1
password_query = SELECT username AS user,password FROM mailbox \
  WHERE username = '%u' AND active='1'

15 . Edit the file /etc/dovecot/conf.d/10-mail.conf with the required information as shown below:

...
mail_location = maildir:/var/mail/vmail/%d/%n
...
mail_uid = vmail
mail_gid = vmail
...
first_valid_uid = 5000
last_valid_uid = 5000
...
mail_privileged_group = mail
...
mail_plugins = quota
...

16 . Modify the information in the file /etc/dovecot/conf.d/10-auth.conf as following:

...
disable_plaintext_auth = yes
...
auth_mechanisms = plain login
...
#!include auth-system.conf.ext
!include auth-sql.conf.ext
...

17 . Edit the file /etc/dovecot/conf.d/10-master.conf as following:

...
service lmtp {
  unix_listener /var/spool/postfix/private/dovecot-lmtp {
    mode = 0600
    user = postfix
    group = postfix
  }
...
}
...
service auth {
  ...
  unix_listener auth-userdb {
    mode = 0600
    user = vmail
    group = vmail
  }
  ...
  unix_listener /var/spool/postfix/private/auth {
    mode = 0666
    user = postfix
    group = postfix
  }
  ...
}
...
service auth-worker {
  user = vmail
}
...
service dict {
  unix_listener dict {
    mode = 0660
    user = vmail
    group = vmail
  }
}
...

18 . Edit the file /etc/dovecot/conf.d/10-ssl.conf as following:

...
ssl = yes
...
ssl_cert = </etc/letsencrypt/live/mail.example.com/fullchain.pem
ssl_key = </etc/letsencrypt/live/mail.example.com/privkey.pem
ssl_dh = </etc/ssl/certs/dhparam.pem
...
ssl_cipher_list = EECDH+AES:EDH+AES+aRSA
...
ssl_prefer_server_ciphers = yes
...

19 . Add the following line to the file /etc/dovecot/conf.d/20-imap.conf

...
protocol imap {
  ...
  mail_plugins = $mail_plugins imap_quota
  ...
}
...

20 . Edit the file /etc/dovecot/conf.d/20-lmtp.conf as following:

...
protocol imap {
  postmaster_address = postmaster@example.com
  mail_plugins = $mail_plugins
}
...

21 . Add a Spam folder in the file /etc/dovecot/conf.d/15-mailboxes.conf:

...
mailbox Drafts {
  special_use = \Drafts
}
mailbox Spam {
  special_use = \Junk
  auto = subscribe
}
mailbox Junk {
  special_use = \Junk
}
...

22 . Configure Dovecot to connect to the MySQL database to manage the quotas, either per domain or per user. It will send a notification by email once the mailbox of a user has reached a certain level of saturation. Edit the file /etc/dovecot/conf.d/90-quota.conf:

quota = dict:User quota::proxy::sqlquota
quota_rule = *:storage=5GB
quota_rule2 = Trash:storage=+100M
quota_grace = 10%%
quota_exceeded_message = Quota exceeded, please contact your system administrator.
quota_warning = storage=100%% quota-warning 100 %u
quota_warning2 = storage=95%% quota-warning 95 %u
quota_warning3 = storage=90%% quota-warning 90 %u
quota_warning4 = storage=85%% quota-warning 85 %u
}

service quota-warning {
executable = script /usr/local/bin/quota-warning.sh
user = vmail

unix_listener quota-warning {
  group = vmail
  mode = 0660
  user = vmail
}
}

dict {
sqlquota = mysql:/etc/dovecot/dovecot-dict-sql.conf.ext

23 . Edit the file /etc/dovecot/dovecot-dict-sql.conf.ext and add the following content. Make sure your MySQL credentials are correct:

...
connect = host=127.0.0.1 dbname=postfixadmin user=postfixadmin password=your_secret_password
...
map {
  pattern = priv/quota/storage
  table = quota2
  username_field = username
  value_field = bytes
}
map {
  pattern = priv/quota/messages
  table = quota2
  username_field = username
  value_field = messages
}
...
# map {
#   pattern = shared/expire/$user/$mailbox
#   table = expires
#   value_field = expire_stamp
#
#   fields {
#     username = $user
#     mailbox = $mailbox
#   }
# }
...

24 . Create the following script, which sends a warning to a user that reaches the capacity limits of his mailbox. Edit the file /usr/local/bin/quota-warning.sh:

#!/bin/sh
PERCENT=$1
USER=$2
cat << EOF | /usr/lib/dovecot/dovecot-lda -d $USER -o "plugin/quota=dict:User quota::noenforcing:proxy::sqlquota"
From: postmaster@example.com
Subject: Quota warning

Your mailbox is $PERCENT% full. Don't forget to make a backup of old messages to remain able to receive mails.
EOF

25 . Make the script executable:

sudo chmod +x /usr/local/bin/quota-warning.sh

And restart dovecot:

service dovecot restart

Your mail server is now ready to be used, and you can create mailboxes at http://your_servers_ip/postfixadmin

Installing Rspamd

To protect yourself from spam and to to increase the trust level of your mails, we use Rspamd and create DKIM and DMARC DNS records.

Installing Redis

Redis is used by Rspamd as as a storage and caching system. It can easily be installed with apt:

sudo apt install redis-server

Installing Rspamd

1 . Add the repository of Rspamd to your apt sources with the following command:

wget -O- https://rspamd.com/apt-stable/gpg.key | sudo apt-key add -
echo "deb http://rspamd.com/apt-stable/ $(lsb_release -cs) main" | sudo tee -a /etc/apt/sources.list.d/rspamd.list

2 . Then update your apt cache and install the tool:

sudo apt update
sudo apt install rspamd

Configuring Rspamd

1 . Once the installation has finished, create the config files for Rspamd in the directory /etc/rspamd/local.d/local.d/.

The file /etc/rspamd/local.d/worker-normal.inc contains information about the port on which Rspamd listens. The default port is 11333, bind it to your localhost by adding the following line to the file:

bind_socket = "127.0.0.1:11333";

2 . Configure a proxy between Postfix and Rspamd, it listens on port 11332 and uses milter to communicate between the two tools. Edit the file /etc/rspamd/local.d/worker-proxy.inc

3 . Set a password for the worker. To generate an encrypted password, run the following command:

rspamadm pw --encrypt -p your_secret_password

Remember to replace your_secret_password with your own password

You will see an output like the following:

rspamadm pw --encrypt -p your_secret_password
$2$93qin9nkifzjpr7taqhs9guua888tnny$dnys6um6xm1gb1amgnz9hocuz7grxuk5z9yjw87psrk6yu641oiy

4 . Edit the file /etc/rspamd/local.d/worker-controller.inc and put the encrypted password into it:

password = "$2$93qin9nkifzjpr7taqhs9guua888tnny$dnys6um6xm1gb1amgnz9hocuz7grxuk5z9yjw87psrk6yu641oiy";

Configure redis to be used with rspamd by editing the file `/etc/rspamd/local.d/classifier-bayes.conf`:

```code
servers = "127.0.0.1";
backend = "redis";

5 . Set the milter headers in the file /etc/rspamd/local.d/milter_headers.conf:

use = ["x-spamd-bar", "x-spam-level", "authentication-results"];

6 . Restart Rspamd:

sudo service rspamd restart

7 . Add an proxy in the Nginx configuration file (for example: /etc/nginx/sites-enabled/mail.example.com.conf):

...
location /rspamd {
    proxy_pass http://127.0.0.1:11334/;
    proxy_set_header Host $host;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
...

8 . Restart Nginx:

sudo service nginx restart

You can access the web interface of Rspamd now at: http://your_servers_ip/rspamd. To authenticate use the password you have set with the rspamadm pw command.

Configuring Postfix

To use Rspamd with Postfix, the configuration has to be updated with postconf:

sudo postconf -e "milter_protocol = 6"
sudo postconf -e "milter_mail_macros = i {mail_addr} {client_addr} {client_name} {auth_authen}"
sudo postconf -e "milter_default_action = accept"
sudo postconf -e "smtpd_milters = inet:127.0.0.1:11332"
sudo postconf -e "non_smtpd_milters = inet:127.0.0.1:11332"

Restart postfix to take the changes into effect:
```code
sudo service postfix restart

Configuring Dovecot

Dovecot is already installed on the server, add the sieve filtering module and integrate it with Rspamd.

1 . Install sieve via apt:

sudo apt-get install dovecot-sieve dovecot-managesieved

2 . Open the file /etc/dovecot/conf.d/20-lmtp.conf and edit is as following:

...
protocol lmtp {
  postmaster_address = postmaster@example.com
  mail_plugins = $mail_plugins sieve
}
...

3 . Open the file /etc/dovecot/conf.d/20-imap.conf and edit is as following:

...
protocol imap {
  ...
  mail_plugins = $mail_plugins imap_quota imap_sieve
  ...
}
...

4 . Edit the file /etc/dovecot/conf.d/20-managesieve.conf as following:

...
service managesieve-login {
  inet_listener sieve {
    port = 4190
  }
}
...
service managesieve {
  process_limit = 1024
}
...

5 . Open and edit the file /etc/dovecot/conf.d/90-sieve.confas following:

plugin {
    ...
    # sieve = file:~/sieve;active=~/.dovecot.sieve
    sieve_plugins = sieve_imapsieve sieve_extprograms
    sieve_before = /var/vmail/mail/sieve/global/spam-global.sieve
    sieve = file:/var/vmail/mail/sieve/%d/%n/scripts;active=/var/vmail/mail/sieve/%d/%n/active-script.sieve

    imapsieve_mailbox1_name = Spam
    imapsieve_mailbox1_causes = COPY
    imapsieve_mailbox1_before = file:/var/vmail/mail/sieve/global/report-spam.sieve

    imapsieve_mailbox2_name = *
    imapsieve_mailbox2_from = Spam
    imapsieve_mailbox2_causes = COPY
    imapsieve_mailbox2_before = file:/var/vmail/mail/sieve/global/report-ham.sieve

    sieve_pipe_bin_dir = /usr/bin
    sieve_global_extensions = +vnd.dovecot.pipe
    ....
}

6 . Create a directory for the sieve scripts:

mkdir -p /var/vmail/mail/sieve/global

7 . Create a global sieve filter in the file /var/vmail/mail/sieve/global/spam-global.sieve. It will move emails marked as spam directly to the spam folder:

require ["fileinto","mailbox"];

if anyof(
    header :contains ["X-Spam-Flag"] "YES",
    header :contains ["X-Spam"] "Yes",
    header :contains ["Subject"] "*** SPAM ***"
    )
{
    fileinto :create "Spam";
    stop;
}

8 . Create a script, named /var/vmail/mail/sieve/global/spam-global.sieve, that will be triggered each time when you manually move an email into the spam folder:

require ["vnd.dovecot.pipe", "copy", "imapsieve"];
pipe :copy "rspamc" ["learn_spam"];

9 . Create a script, named /var/vmail/mail/sieve/global/report-ham.sieve, that will be triggered each time when you move an email out of the spam folder:

require ["vnd.dovecot.pipe", "copy", "imapsieve"];
pipe :copy "rspamc" ["learn_ham"];

10 . Compile the sieve scripts and set permissions:

sievec /var/vmail/mail/sieve/global/spam-global.sieve
sievec /var/vmail/mail/sieve/global/report-spam.sieve
sievec /var/vmail/mail/sieve/global/report-ham.sieve
sudo chown -R vmail: /var/vmail/mail/sieve/

Creating DKIM keys

DomainKeys Identified Mail (DKIM) is an email authentication method designed to detect email spoofing. It allows the to verify the origin of an email by affixing a digital signature to it. Verification of the signature is carried out using the signer’s public key published in the DNS. It can be used to detect fraudulent mails.

1 . Create a new directory to store the DKIM key and generate a new DKIM keypair by using the rspamadm utility. In the following example we use mail as a DKIM selector. It will generate a keypair that can be used for all domains handled by the mail server.

mkdir /var/lib/rspamd/dkim/
rspamadm dkim_keygen -b 2048 -s mail -k /var/lib/rspamd/dkim/mail.key > /var/lib/rspamd/dkim/mail.pub

You will find two files in the directory:

  • mail.key - The privatse key file
  • mail.pub - The public key file

2 . Create a new file /etc/rspamd/local.d/dkim_signing.conf to tell Rspamd where to look for the DKIM key and the selector name. The last line will enable DKIM signing for alias sender addresses:

selector = "mail";
path = "/var/lib/rspamd/dkim/$selector.key";
allow_username_mismatch = true;

3 . Rspamd supports also ARC signatures, use the same configuration file and copy it

cp  /etc/rspamd/local.d/dkim_signing.conf /etc/rspamd/local.d/arc.conf

4 . Restart Rspamd:

sudo service rspamd restart

DNS settings

To sign your mails with DKIM, you have to add the public key to your DNS zone.

1 . Retrieve the key:

cat /var/lib/rspamd/dkim/mail.pub

It will provide you an output like the following:

mail._domainkey IN TXT ( "v=DKIM1; k=rsa; "
	"p=MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAxzllrHkbUwSR24B6iG+TgNTOU43lZhTPJemo8PKXkgaVppGJ57tlWOe9U321Qk+Ksk9qoukR4f39TCMQdAgtEPFpWSBWJJE9C2SmNz38SmhTC0AkvIzBxCdatitK2aWjHq4s9bsoQ1gIQlXKM+V7GbN2LFCBfvAU7ElBQk+QG2DuxGD/XNDLQWloYEWcqkUfxlHr0znoY86jkglVZ"
	"nhi/cAoE0SbzjphCtibT9T1w6AztxV1yK2VTJPpBFdtAsP1Sa3GDbTn0HATHUJI8eOIXtFcIBbYisiOIWjisE3TXFpvkS69Q0gvxVFYDnftLvsf5AticeygdMOVbK1o3T4Z7QIDAQAB"
) ;

You can add the information as a TXT record in the DNS zone of your domain.

Installing Roundcube Webmail

To read your mails comfortable and directly within your web browser, we will install a Roundcube web mail interface.

1 . Start by installing all PHP dependencies:

sudo apt install php-intl php-mail-mime php-net-smtp php-net-socket php-pear php-xml php7.2-intl php7.2-xml php7.2-gd php7.2-gd php-imagick

2 . Login to your MariaDB server and create a MySQL database for Roundcube:

mysql -u root -p
CREATE DATABASE roundcubemail;
GRANT ALL ON roundcubemail.* TO 'roundcube'@'localhost' IDENTIFIED BY 'your_secret_password';
FLUSH PRIVILEGES;
\q

3 . Download roundcube, unpack it and move it into the web directory:

wget https://github.com/roundcube/roundcubemail/releases/download/1.3.6/roundcubemail-1.3.6-complete.tar.gz
tar xzf roundcubemail-1.3.6-complete.tar.gz
sudo mv roundcubemail-1.3.6 /var/www/webmail
rm roundcubemail-1.3.6-complete.tar.gz

4 . Change the ownership of the folder and all files in it to the www-data user:

chown -R www-data: /var/www/webmail

5 . Edit the Nginx configuration (/etc/nginx/sites-enabled/mail.example.com) of your server and add the information for the roundcube directory:

...
location /webmail {
   index index.php;
   try_files $uri $uri/ /webmail/index.php;
}
location ~ ^/webmail/(README|INSTALL|LICENSE|CHANGELOG|UPGRADING)$ {
   deny all;
}
location ~ ^/webmail/(bin|SQL|config|temp|logs)/ {
   deny all;
}
...

6 . Restart Nginx:

service nginx restart

7 . Launch installation from https://your_server_ip/webmail/installer/ and enter all the required information.

8 . Remove the installer for security reasons:

sudo rm -rf /var/www/roundcubemail/installer

Discover a New Cloud Experience

Deploy SSD Cloud Servers in seconds.