As a software engineer or network administrator you will likely encounter a situation where you need to setup an email server that is only intended to send email but not accept incoming mail. This is a common setup for simple web applications which need to communicate with external users. There are two methods that I typically use in these situations, the first being a basic postfix setup using Debian or Ubuntu, and the second method is using AWS’s SES (simple email service).
Let’s start with the Postfix setup. The benefits of this setup is that it isn’t too complicated and it gives you the most flexibility. The downside is that if you are setting this up on a VPS (like Digital Ocean, Linode, etc) you are at the mercy of the reputation of the IP address that you inherit. I’ve gotten burned by this more than once, where I have a web application that needed to scale out and one of the new nodes was assigned an IP address that was previously used by a site that sent nothing but SPAM. So all email on that address was being blocked by about all SPAM filters on the face of the planet. In this case there isn’t much you can do, except request a new IP or spin up a new node.
Ok, let’s start by installing a new Ubuntu server install with a static IP. You will also need to setup you DNS records as well for your domain, which we won’t cover here.
Let’s start by updating your OS and installing the mailutils package with:
sudo apt update sudo apt upgrade sudo apt install mailutils
At some point in the installation a text-based dialog window will pop-up asking for a Postfix or mail server configuration. In this dialog select Internet Site.
Next you’ll be prompted to enter a System Mail Name. In this screen, enter your mail server’s domain name, like “example.com”.
Now we need to lock down our server configuration to only accept mail from localhost. To do this we are going to edit the postfix main.cf file with the following command:
sudo nano /etc/postfix/main.cf
In the main.cf file we need to locate the line:
inet_interfaces = all
and replace it with
inet_interfaces = loopback-only
After making the changes and saving the main.cf file we’ll need to restart postfix with:
sudo systemctl restart postfix
Now let’s test out Postfix and make sure we can send an email, this can be done with the mail command as follows:
echo "Test" | mail -s "Subject" firstname.lastname@example.org
Now that you have a basic send-only mail server setup, we would recommend testing to ensure that you haven’t misconfigured your server causing it to act as an open-relay. There are a number of sites that can do this for you, just Google for one. At this point you’ll need to ensure your DNS settings are configured correctly for your email server and you’ll want to test with all the major email providers to ensure that they will accept your email.
Alternative Solution – AWS Simple Email Service
I am the kind of person that loves building things myself especially when it comes to technology, but I must admit that in most cases, I’ll use this method because I’ve been burned before. AWS SES is a service that allows you to send email using Amazon’s AWS service. This is a paid service, but it is very reasonable, at the time of writing this it cost $0.10 per 1,000 email messages sent.
One of the benefits of this service is that most of the boring stuff like DKIM is all setup by Amazon, but the biggest selling point to me is that I can be notified about email delivery failures and bounced messages using AWS’s SNS service. To me, this feature makes it worth while as Amazon will tell me via a simple JSON object if the sending of a message has failed. This can be difficult to do with Postfix, so this is why SES has become my preferred method of mail delivery.
Lastly, SES doesn’t really use any proprietary code or API, you are provided with a username and password as well as mail server settings, and you send your messages as you normally would to any other SMTP server. This may seem like I am gushing about SES, but this isn’t a paid promotion, I just really like the service. After tracking down issues with being blocked by certain email providers, and having customers getting upset because all their email messages are not being delivered, I decided this was the best choice for me. For more information about SES, visit:
Thanks and happy coding!