How to Setup and Configure your own E-mail server – Debian

Introduction:

Having your own email server can be very helpful and advantageous if your someone like me, someone who tends to not only receive and send copious amounts of emails but also lots of files and media. It isn’t uncommon for my email chains to run into 20-30+ messages with media and files for the work i do with my clients.

It can also be said that having your own email server requires some constant oversight and security monitoring (for which there are tools for). It is important to note this, as if not handled correctly you may find your email domain being blacklisted and there have been cases of people not being able to register even new domains for email services with their name and/or other details that were previously blacklisted for what is usually not their fault.

On the above statement i remember coming across these cases a while back and if i come across them again i will link the articles in this post!

Requirements:

To follow this tutorial/guide i will be setting up the server using Postfix, Dovecot and MySQL. Optionally you can choose to install a web based email client such as SquirrelMail.

While you can also use alternatives for the above such as MariaDB instead of MySQL and while that is great! This guide will follow the listed above and if you deviate you may have to change some of the syntax used in terminal/console.

In addition to the above software you will also be required to do the following before we can even begin.

  • Make sure you have MySQL or your database of choice setup and ready to go!
  • This should be done by default but make a user with full privileges can make this process much easier.
  • Have a domain name and make sure it is pointing to your server
  • Setup a FQDN (Fully Qualified Domain Name)

Optional extras:

  • phpMyAdmin – This can make database handling easier if you don’t like or are not comfortable with terminal for database queries.
  • SSL Certificate – This would be a good idea all though not required.

Upon Completion:

Once you have following this guide you will be able to operate what most would call a fully function email server. That is you will be able to send and receive mail, add new users and aliases as well as virtual domains all while keeping it generally secure from spam.

Lets Begin: Part One – Install Software & Packages

Firstly lets begin by instilling the various packages and software we need to get this going. Firstly we are going to install Postfix and Dovecot and its various extensions to work with MySQL and server.

apt-get install postfix postfix-mysql dovecot-core dovecot-imapd dovecot-lmtpd dovecot-mysql

The following screen should pop up and display:

postfix_popup

Select the option Internet Site and continue to the next screen.

The installation of Postfix will require you to specify a mail name for the system, you can use your domain name or your FQDN if you wish.

postfix_systemname

Now that Postfix is all setup following those two easy steps we can move onto the next step which focuses on the Database and various users, aliases and domains.

Database: Part Two – Setup MySQL, Aliases, Virtual Domains and Users

After part one is completed we move onto the setting up MySQL and the databases and tables to hold the Users, Aliases and Domains.

For the purpose of this guide i will be naming my database emailserver, but you can call the database what ever name you wish. Just remember the name!

This guide will follow the terminal/console method for MySQL configuration. If you use phpMyAdmin then you can still follow but pay attention to the sections in which we create the database, tables and data.

First create the database:

mysqladmin -p create emailserver

Login to MySQL as the root user:

mysql -u root -p

If you enter your login details correctly you will be displayed with the following MySQL prompt:

mysql >

The first user we will create is actually going to a agent of sorts, rather then a specified user you will use in future. This user will be the authentication mail user that verifies and authenticates email activity on the server with specific privileges.

mysql > GRANT SELECT ON emailserver.* TO 'usermail'@'127.0.0.1' IDENTIFIED BY 'mailpassword';

It is necessary to reload MySQL privileges to make sure they are applied correctly following the above command.

mysql > FLUSH PRIVILEGES;

Next we need to get into the emailserver database to make the tables we need to store the various data.

mysql> USE emailserver;

The first table we will create is a table for holding the authorised domain names on the server.

CREATE TABLE `virtual_domains` (
`id`  INT NOT NULL AUTO_INCREMENT,
`name` VARCHAR(50) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

Next we are going to create a table for the users, this will store email addresses and associated passwords for each user. Its important to note also in this step that you need to specify a domain or domains for each user.

CREATE TABLE `virtual_users` (
`id` INT NOT NULL AUTO_INCREMENT,
`domain_id` INT NOT NULL,
`password` VARCHAR(106) NOT NULL,
`email` VARCHAR(120) NOT NULL,
PRIMARY KEY (`id`),
UNIQUE KEY `email` (`email`),
FOREIGN KEY (domain_id) REFERENCES virtual_domains(id) ON DELETE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

Lastly in this step we will create a table of virtual aliases which will handle the domain to the various email address for the users specified in the above table.

CREATE TABLE `virtual_aliases` (
`id` INT NOT NULL AUTO_INCREMENT,
`domain_id` INT NOT NULL,
`source` varchar(100) NOT NULL,
`destination` varchar(100) NOT NULL,
PRIMARY KEY (`id`),
FOREIGN KEY (domain_id) REFERENCES virtual_domains(id) ON DELETE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

Now we have created the necessary tables we can begin to populate them with data!

Now we are going to populate the virtual domains table with some domains. You can add as many as you want but i will only be adding one in this guide. You will see i add both the main domain (example.com) and the FQDN (hostname.example.com)

INSERT INTO `emailserver`.`virtual_domains`
(`id` ,`name`)
VALUES
('1', 'example.com'),
('2', 'hostname.example.com');

We are now going to add the email address and passwords for each domain. Since we have just one domain that will be just 1. Make sure to alter the information in the password and email sections with the emails and passwords you wish for them.

INSERT INTO `emailserver`.`virtual_users`
(`id`, `domain_id`, `password` , `email`)
VALUES
('1', '1', ENCRYPT('firstpassword', CONCAT('$6$', SUBSTRING(SHA(RAND()), -16))), 'email1@example.com'),
('2', '1', ENCRYPT('secondpassword', CONCAT('$6$', SUBSTRING(SHA(RAND()), -16))), 'email2@example.com');

Now we are going to link the emails to the authenticated email we created earlier. Its handy in this way to think of the authenticated email address as like a post master who then delivers the emails to the recipients (the email addresses specified above).

INSERT INTO `emailserver`.`virtual_aliases`
(`id`, `domain_id`, `source`, `destination`)
VALUES
('1', '1', 'alias@example.com', 'email1@example.com');

Now we can jump out of MySQL and finish with that step.

 mysql > exit

 Postfix Config: Part Three – Configuring Postfix

Now we are going to configure postfix to deal with SMTP connections and distribute to the various email addresses.

Before we start we should make a backup of the default config file just incase you wish to revert to it later.

cp /etc/postfix/main.cf /etc/postfix/main.cf.orig

Open main.cf file using nano or your favourite terminal/console editor:

nano /etc/postfix/main.cf

Next we need to comment the TLS Parameters and change other parameters.


# TLS parameters
#smtpd_tls_cert_file=/etc/ssl/certs/ssl-cert-snakeoil.pem
#smtpd_tls_key_file=/etc/ssl/private/ssl-cert-snakeoil.key
#smtpd_use_tls=yes
#smtpd_tls_session_cache_database = btree:${data_directory}/smtpd_scache
#smtp_tls_session_cache_database = btree:${data_directory}/smtp_scache 
smtpd_tls_cert_file=/etc/ssl/certs/dovecot.pem
smtpd_tls_key_file=/etc/ssl/private/dovecot.pem
smtpd_use_tls=yes
smtpd_tls_auth_only = yes

Next we are going to change the following parameters below the TLS settings that we have changed in the previous step:


smtpd_sasl_type = dovecot
smtpd_sasl_path = private/auth
smtpd_sasl_auth_enable = yes
smtpd_recipient_restrictions =
permit_sasl_authenticated,
permit_mynetworks,
reject_unauth_destination

We need to comment the mydestination default settings and replace it with localhost. This change allows your VPS to use the virtual domains inside the MySQL table.


#mydestination = example.com, hostname.example.com, localhost.example.com, localhost
mydestination = localhost 

Check that myhostname parameter is set with your FQDN.


myhostname = hostname.example.com

Append the following line for local mail delivery to all virtual domains listed inside the MySQL table.

virtual_transport = lmtp:unix:private/dovecot-lmtp

Finally, we need to add these three parameters to tell Postfix to configure the virtual domains, users and aliases.


virtual_mailbox_domains = mysql:/etc/postfix/mysql-virtual-mailbox-domains.cf
virtual_mailbox_maps = mysql:/etc/postfix/mysql-virtual-mailbox-maps.cf
virtual_alias_maps = mysql:/etc/postfix/mysql-virtual-alias-maps.cf

Note: Compare these changes with this file to detect mistakes or errors:

https://www.dropbox.com/s/x9fpm9v1dr86gkw/etc-postfix-main.cf.txt

We are going to create the final three files that we append in the main.cf file to tell Postfix how to connect with MySQL.

First we need to create the mysql-virtual-mailbox-domains.cf file. It’s necessary to change the values depending your personal configuration.


nano /etc/postfix/mysql-virtual-mailbox-domains.cf
		
user = usermail
password = mailpassword
hosts = 127.0.0.1
dbname = emailserver
query = SELECT 1 FROM virtual_domains WHERE name='%s'

Then we need to restart Postfix.


service postfix restart

We need to ensure that Postfix finds your domain, so we need to test it with the following command. If it is successful, it should returns 1:


postmap -q example.com mysql:/etc/postfix/mysql-virtual-mailbox-domains.cf

Then we need to create the mysql-virtual-mailbox-maps.cf file.


nano /etc/postfix/mysql-virtual-mailbox-maps.cf 
		
user = usermail
password = mailpassword
hosts = 127.0.0.1
dbname = emailserver
query = SELECT 1 FROM virtual_users WHERE email='%s'

We need to restart Postfix again.

service postfix restart

At this moment we are going to ensure Postfix finds your first email address with the following command. It should return 1 if it’s successful:

postmap -q email1@example.com mysql:/etc/postfix/mysql-virtual-mailbox-maps.cf

Finally, we are going to create the last file to configure the connection between Postfix and MySQL.


nano /etc/postfix/mysql-virtual-alias-maps.cf
		
user = usermail
password = mailpassword
hosts = 127.0.0.1
dbname = emailserver
query = SELECT destination FROM virtual_aliases WHERE source='%s'

Restart Postfix

service postfix restart

We need to verify Postfix can find your aliases. Enter the following command and it should return the mail that’s forwarded to the alias:

postmap -q alias@example.com mysql:/etc/postfix/mysql-virtual-alias-maps.cf

If you want to enable port 587 to connect securely with email clients, it is necessary to modify the /etc/postfix/master.cf file


nano /etc/postfix/master.cf

We need to uncomment these lines and append other parameters:


submission inet n       -       -       -       -       smtpd
-o syslog_name=postfix/submission
-o smtpd_tls_security_level=encrypt
-o smtpd_sasl_auth_enable=yes
-o smtpd_client_restrictions=permit_sasl_authenticated,reject

In some cases, we need to restart Postfix to ensure port 587 is open.

service postfix restart

Note: You can use this tool to scan your domain ports and verify that port 25 and 587 are open (http://mxtoolbox.com/SuperTool.aspx)

 

 

 

Testing your Mail Server

There are many websites and ways to test how well your email server functions. This gives you a great way to see how other servers, and thus other people will treat and see your emails. This is crucial as you will want to make sure your emails are not being treated as spam by other servers due to what can be tiny errors in the mail server or the domain handling your email.

I have used a number of websites for such tasks, mail tester is a very nicely designed tool and gives you good feedback as well as email reports to a specified email of your choosing.

mail-tester.com

Once you have done all the above, using this tool or any other you feel you like will help you apply the finishing touches to your email server.


Robert

Robert Mizen is a Producer, Tech Consultant and all things nerdy person. Interested in Games, Apps, Web, Green Tech, Astrophysics and Travel. This website is a outlet to express so i dont explode.

2 Comments

Robert · 2016-11-01 at 16:55

My statement about being blacklisted at the near beginning of the post is important and i will find the articles referencing that information.

Worlds Quickest Web Server Tutorial (Ubuntu 16.04) - TVO Robert Mizen · 2018-10-15 at 14:58

[…] Setting up your own Email Server […]

Leave a Reply

Your email address will not be published.

This site uses Akismet to reduce spam. Learn how your comment data is processed.