Installation:Debian:Postfix
Contents
Needed Packages
On Debian GNU/Linux you need to install the following packages:
- postfix (Version 2)
- postfix-mysql
- postfix-tls (for Auth-SMTP)
- postfix-pcre
- libsasl2
- libsasl2-modules
- libsasl2-modules-sql
- openssl
- amavisd-new, zoo, lha, unarj, unzip (if you want virus scanning)
Installation
On Debian GNU/Linux use this command to install all at once:
apt-get install postfix postfix-mysql postfix-tls postfix-pcre libsasl2 libsasl2-modules libsasl2-modules-sql openssl
If you want to use amavisd-new, then run
apt-get install amavisd-new unzip
Please create a new systemuser named "vmail" to your system.
On Debian GNU/Linux use this command:
adduser --disabled-password --disabled-login --gecos "Mail user" vmail
After the creation, type this to get uid and gid of the vmail user, we will need those values in Postfix' main.cf.
bash #> id vmail uid=1005(vmail) gid=1005(vmail) Gruppen=1005(vmail) bash #>
Postfix configuration
First, you have to configure postfix to connect to mysql database which is installed via phpmywebhosting.
First of all an important note: Remember that Postfix runs in a chroot environment. Thus it would not be able to access MySQL's socket file at /var/run/mysqld/mysqld.sock. There are two ways to work around this: Mario Duve (et al) propose an addition to the start section of /etc/init.d/postfix like this:
if [ -e /var/spool/postfix/var/run/mysqld/mysqld.sock ]; then rm /var/spool/postfix/var/run/mysqld/mysqld.sock fi mkdir -p /var/spool/postfix/var/run/mysqld chown mysql /var/spool/postfix/var/run/mysqld ln /var/run/mysqld/mysqld.sock /var/spool/postfix/var/run/mysqld/mysqld.sock
In case of power failure postfix won't start working because the socket of mysql is not valid. To prevent this edit /etc/init.d/postfix and add the above lines in the start section under echo -n "Starting mail transport agent: Postfix". Result is:
case "$1" in start) echo -n "Starting mail transport agent: Postfix" if [ -e /var/spool/postfix/var/run/mysqld/mysqld.sock ]; then rm /var/spool/postfix/var/run/mysqld/mysqld.sock fi mkdir -p /var/spool/postfix/var/run/mysqld chown mysql /var/spool/postfix/var/run/mysqld ln /var/run/mysqld/mysqld.sock /var/spool/postfix/var/run/mysqld/mysqld.sock # see if anything is running chrooted. [...]
Also take care, that postfix is started after mysql. Check it with the following command:
bash #> ls /etc/rc$(grep initdefault /etc/inittab | cut -d: -f2).d/ | grep -E "(postfix|mysql)" S20mysql S20postfix bash #>
If it is like above, everything is alright. If not, delete the links in /etc/rc{runlevel}.d/ and create them new.
Or use the real hostname of the MySQL server instead of "localhost". This way database lookups will be done via UDP instead of UNIX sockets. In this case you will need to comment out the line "skip-networking" in the /etc/mysql/my.cnf file to enable the UDP listener.
Debian: /etc/postfix/main.cf
# basic settings command_directory = /usr/sbin daemon_directory = /usr/lib/postfix program_directory = /usr/lib/postfix myorigin = [your local domain] mydomain = [your local domain] myhostname = [hostname.your local domain] mydestination = $myhostname, localhost.$mydomain, $mydomain, $transport_maps mynetworks = 127.0.0.0/8 # virtual domain and delivery settings virtual_alias_domains = virtual_alias_maps = mysql:/etc/postfix/mysql-virtual_forwardings.cf mysql:/etc/postfix/mysql-virtual_email2email.cf virtual_mailbox_domains = mysql:/etc/postfix/mysql-virtual_domains.cf virtual_mailbox_maps = mysql:/etc/postfix/mysql-virtual_mailboxes.cf virtual_mailbox_base = /home/vmail/ # [VMAIL-UID] virtual_uid_maps = static:1005 # [VMAIL-UID] virtual_gid_maps = static:1005 # define which email is accepted for delivery only # alias_maps means: addresses in the MySQL aliase table # virtual_mailbox_maps: addresses in the MySQL virtual table # unix:passwd.byname: addresses of local users in /etc/passwd (optional) local_recipient_maps = $alias_maps $virtual_mailbox_maps unix:passwd.byname # settings for authenticated SMTP smtpd_sasl_auth_enable = yes smtpd_recipient_restrictions = permit_mynetworks, permit_sasl_authenticated, check_relay_domains smtpd_sasl_security_options = noanonymous broken_sasl_auth_clients = yes # some other options smtpd_banner = $myhostname ESMTP $mail_name (Debian/GNU) # or FreeBSD ;-) setgid_group = postdrop biff = no # appending .domain is the MUA's job. append_dot_mydomain = no relayhost = mailbox_size_limit = 0 recipient_delimiter = + message_size_limit = 10000000 # SSL smtpd_use_tls = yes smtpd_tls_cert_file = /etc/postfix/smtpd.cert smtpd_tls_key_file = /etc/postfix/smtpd.key
As you can see we will not be querying the MySQL database according to definitions in /etc/postfix/mysql-aliases.cf.
For this to work you need to create these files first. They define how Postfix accesses the database and how you named the fields. Just copy and paste them:
/etc/postfix/mysql-virtual_domains.cf
user = postfix password = postfix-password dbname = pmwh table = postfix-transport select_field = destination where_field = domain hosts = localhost
/etc/postfix/mysql-virtual_forwardings.cf
user = postfix password = postfix-password dbname = pmwh table = postfix-forwardings select_field = destination where_field = source hosts = localhost
/etc/postfix/mysql-virtual_mailboxes.cf
user = postfix password = postfix-password dbname = pmwh table = postfix-users select_field = maildir where_field = email hosts = localhost
/etc/postfix/mysql-virtual_email2email.cf
user = postfix password = postfix-password dbname = pmwh table = postfix-users select_field = email where_field = email hosts = localhost
Make sure to run
bash #> chmod o= /etc/postfix/mysql-* bash #> chgrp postfix /etc/postfix/mysql-*
Now we configure postfix to understand authenticated SMTP.
Imagine your users fetch their email using POP3. Now they need a way to send mails via your mail server. For security reasons Postfix allows users in the local (=trusted) network to send emails. (You obviously want this security if you don't want to work as an open relay for spammers.) My suggestion is that your users use authenticated SMTP. This means that their email clients provide a username and password to the mail server to make them "trusted". Most email cilents have this feature included.
Setting authenticated SMTP isn't that complicated. The only pitfall is that Debian runs Postfix in a chroot'ed environment by default. ("chroot'ed" means that Debian pretends that the "/var/spool/postfix" directory is pretended to be "/" - so Postfix cannot move out of this secure subdirectory. Anyone who finds a security problem and messes with Postfix can only do harm to that very subdirectory and not screw your whole system)
The second step is to make SASL use the PAM for authentication. This is easy. Just put the following lines in
/etc/postfix/sasl/smtpd.conf
pwcheck_method: auxprop auxprop_plugin: sql mech_list: plain login cram-md5 digest-md5 sql_engine: mysql sql_hostnames: localhost sql_user: postfix sql_passwd: postfix-password sql_database: pmwh sql_select: select password from users where email='%u@%r'
Use TLS to encrypt SMTP traffic
An important step is to encrypt the SMTP session. Otherwise the username and password could be transmitted in a very insecure way if the mail client chose to use one of plaintext authentication methods). So I encourage you to encrypt that communication using TLS. TLS is short for Transport Layer Security (RFC2246) and in short terms uses SSL (Secure Socket Layer) which encrypts the mail connection between the road-warrior and the mail server.
First you will need an SSL certificate. If you don't want to pay for one from your favorite trustcenter you can well use a self-signed one. (Personal note: I wonder how paying for something makes it more trusted.) The only drawback: the mail client does not know about your CA (certificate authority) and will spit out a warning to the user. Either tell the users to ignore the warning or let them install the certificate on their computers.
For a certificate that is valid for one year for the hostname smtp.domain.tld you would type this:
openssl req -new -outform PEM -out smtpd.cert -newkey rsa:2048 -nodes -keyout smtpd.key -keyform PEM -days 365 -x509
You will then be asked a few question about the fields of the certificate. It does not matter what you enter. Just fill the fields. One exception though - the "Common Name" must be the hostname of your mail server. Example session:
Country Name (2 letter code) [AU]:DE State or Province Name (full name) [Some-State]:Oldenburg Locality Name (eg, city) []:Oldenburg Organization Name (eg, company) [Internet Widgits Pty Ltd]:ladse.de PHPMyWebHosting Organizational Unit Name (eg, section) []:Master of Disaster Common Name (eg, YOUR name) []:smtp.domain.tld Email Address []:postmaster@domain.tld
After a short moment you will get two files: "smtpd.key" (the private key file) and "smtpd.cert" (the certificate). Move these two files into /etc/postfix.
Make sure at least the key file is not readable for the whole wide world:
chmod o= /etc/postfix/smtpd.key
A quick test
Run postfix reload to restart Postfix. Run
telnet localhost 25
and enter
EHLO anywhere.org
You should find a line reading
250-STARTTLS
Bingo - TLS is running.
Virus filtering
Now that you operate your own professional email server you may offer your users a little more service: scanning incoming emails for viruses. Good news: it is perfectly easy to install. Bad news: it will most likely mean you have to spend money because good antivirus software does not come for free (yet).
Let's get to work. First make sure you installed the amavisd-new package. Amavis is a piece of software that gets all emails forwarded, scans them using an external virus scanner and re-injects them into your mail system. It is important to note that Amavis does not include a virus scanner - it is just an interface between Postfix and your favorite virus scanner. So make sure you have a virus scanner already installed and keep it up-to-date.
Now please take a look at the /etc/amavis/amavisd.conf (FreeBSD 5.3: /usr/local/etc/amavisdconf) file. All configuration you find here are well explained and should be easy to edit. Make sure that you configure at least one virus scanner in the first part of the file and have the following options set:
Debian: /etc/amavis/amavisd.conf
$forward_method = 'smtp:127.0.0.1:10025' $inet_socket_port = 10024;
To get clamav, a free virus scanner, run the following command on
bash #> apt-get install clamav clamav-freshclam clamav-testfiles clamav-daemon clamav-base spamassassin
Give systemuser "clamav" permissions to scan amavis spool files
bash #> usermod -G amavis clamav
Restart the amavisd:
bash #> /etc/init.d/amavis restart
amavisd-new has a lot, lot more options to use other scanners. Most of them are "free" for uncommercial use, but closed source. So make up your mind if you want them or not. If you decide to install another, you just have to uncomment the designated part in amavisd.conf - in most cases.
The last thing to do is tell Postfix that you want to have all your emails scanned. First edit /etc/postfix/main.cf and add the following line:
content_filter = smtp-amavis:[127.0.0.1]:10024
Now you have told Postfix that you want to use the "content_filter = smtp-amavis:[127.0.0.1]:10024" transport method on all emails. You may also consider setting "soft_bounce = yes" temporarily to make sure emails do not get bounced when something goes wrong. Emails will stay in your mail queue if you set this to true.
Finally tell Postfix what you mean by "content_filter = smtp-amavis:[127.0.0.1]:10024". Add this section to the
/etc/postfix/master.cf
smtp-amavis unix - - n - 2 smtp -o smtp_data_done_timeout=1200 -o disable_dns_lookups=yes 127.0.0.1:10025 inet n - n - - smtpd -o content_filter= -o local_recipient_maps= -o relay_recipient_maps= -o smtpd_restriction_classes= -o smtpd_client_restrictions= -o smtpd_helo_restrictions= -o smtpd_sender_restrictions= -o smtpd_recipient_restrictions=permit_mynetworks,reject -o mynetworks=127.0.0.0/8 -o strict_rfc821_envelopes=yes
Restart Postfix (postfix reload) and you are set. You may want to watch the log file (tail -f /var/log/mail.log) and send a test mail. You should find a line like "X-Virus-Scanned: by AMaViS snapshot-20020222" in the email header. To make sure that your system handles infected emails correctly you may want to attach 'eicar.com'. Eicar is not a virus but a well-known (to virus scanners) signature to test if your virus recognition works. When you send this "infected" email to yourself you will receive an alert from Amavis with subject "VIRUS IN YOUR MAIL".
A last word to explain how Amavis works. Postfix receives your mail and pipes the email as defined in your "vscan" transport method into the amavis tool. Amavis will then use the configured virus scanner to scan all attachments. If the attachments are archives it will even use the archive tools to unpack them. After scanning the files it will contact Postfix on localhost's port 10025 and re-inject the email into the delivery process. But this time it sets the "content_filter" option to nothing and thus bypasses the content scanning this time. You will also see this behaviour in your /var/log/mail.log file. First you will see a "relay=vscan" and then a "relay=local".
Amavisd can also be quite intense. Don't shoot me, but after all it's "just" Perl. ;-) Keep in mind.
In case you are not authorized, make sure you tail the auth.log (probably to be found in /var/log) and also use "postfix check" to see if you have any issues open. So for example, if your permissions are screwed up and postfix can not find something, it will most likely tell you.
- Open issues
If you have been successful in one of the following issues then please tell us so we can include the parts here:
- Enforcing quotas during delivery
- how to integrate postgrey with the Debian/GNU installation