Virtuelle Benutzer und Domains mit Postfix, Courier und MySQL (Ubuntu 6.10 Edgy Eft)

Version 1.0
Author: Falko Timme


Diese Anleitung unterliegt dem Copyright (c) 2007 von Falko Timme. Sie stammt von einem Tutorial von Christoph Haas, welches Du auf http://workaround.org findest. Du kannst diese Anleitung unter der Creative Commons Lizenz 2.5 oder jeder späteren Version verwenden.
Diese Anleitung veranschaulicht, wie man einen Mail Server (basierend auf Postfix) installiert, der auf virtuellen Benutzern und Domains basiert, d.h. Benutzer und Domains, die sich in einer MySQL Datenbank befinden. Weiterhin werde ich die Installation und Konfiguration von Courier (Courier-POP3, Courier-IMAP) aufzeigen, damit sich Courier gegenüber der gleichen MySQL Datenbank authentifizieren kann, die Postfix verwendet.

Der daraus resultierende Postfix Server unterstützt SMTP-AUTH und TLS sowie Quota (Quota ist in Postfix standardmäßig nicht enthalten, ich werde zeigen, wie Du Dein Postfix entsprechend patchen kannst). Passwörter werden in der Datenbank in verschlüsselter Form gespeichert (die meisten Dokumente arbeiten mit normalen Textpasswörtern, das ist ein Sicherheitsrisiko). Zusätzlich behandelt diese Anleitung die Installation von Amavisd, SpamAssassin und ClamAV, damit E-Mails auf Spam und Viren gescannt werden.

Der Vorteil eines solchen "virtuellen" Setups (virtuelle Benutzer und Domains in einer MySQL Datenbank) besteht darin, dass es weitaus leistungsfähiger als ein Setup ist, das auf "realen" Systembenutzern basiert. Mit diesem virtuellen Setup kann Dein Mail Server Tausende von Domains und Benutzern bewältigen. Außerdem ist es einfacher zu verwalten, da Du nur mit der MySQL Datenbank zu tun hast, wenn Du neue Benutzer/Domains hinzufügst oder vorhandene bearbeitest. Keine postmap Befehle mehr zum Erstellen von db Dateien, kein Neuladen von Postfix mehr, etc. Zur Administration der MySQL Datenbank kannst Du web-basierte Tools wie phpMyAdmin verwenden, die auch in dieser Anleitung installiert werden. Der dritte Vorteil besteht darin, dass Benutzer eine E-Mail Adresse als Benutzernamen haben (anstelle eines Benutzernamens und einer E-Mail Adresse), was einfacher zu verstehen und zu behalten ist.

Diese Anleitung ist ein praktischer Leitfaden; theoretisches Hintergrundwissen wird nicht abgedeckt. Dies wird in zahlreichen anderen Dokumenten im Web behandelt.

Diese Anleitung ist ohne jegliche Gewähr! Ich möchte an dieser Stelle darauf hinweisen, dass dies nicht der einzige Weg ist, ein solches System einzurichten. Es gibt viele Möglichkeiten dieses Ziel zu erreichen - dies ist der Weg, den ich gewählt habe. Ich übernehme keine Garantie, dass dies auch bei Dir funktioniert!!

1 Vorbemerkung

Diese Anleitung basiert auf Ubuntu 6.10 (Edgy Eft). Du solltest also eine Ubuntu Basisinstallation aufsetzen, bevor Du mit dieser Anleitung weiter machst. Das System sollte eine statische IP Adresse haben. Ich verwende in dieser Anleitung 192.168.0.100 als meine IP Adresse und server1.example.com als den Hostnamen.

Ich führe lieber alle Schritte als Root-Benutzer aus. Wenn Du also noch kein Root Login erstellt hast, solltest Du dies nun tun:

sudo passwd root

Melde Dich danach als Root-Benutzer an:

su

Wenn Du lieber als normaler Benutzer anstatt als Root-Benutzer arbeiten möchtest, dann vergiss nicht sudo vor alle Befehle dieser Anleitung zu setzen. Wenn ich also dies ausführe

apt-get update

solltest Du stattdessen dies ausführen

sudo apt-get update


2 Installation von Postfix, Courier, Saslauthd, MySQL, phpMyAdmin

Bevor wir diese Pakete installieren können, müssen wir /etc/apt/sources.list modifizieren und die universe Paketdatenbank aktivieren. Vergewissere Dich also, dass Du folgende Zeilen aktiviert hast:

vi /etc/apt/sources.list


[...]
deb http://de.archive.ubuntu.com/ubuntu/ edgy universe deb-src http://de.archive.ubuntu.com/ubuntu/ edgy universe [...]
Führe dann dies aus

apt-get update

um Deine Paketdatenbank zu aktualisieren.

Um Postfix, Courier, Saslauthd, MySQL und phpMyAdmin zu installieren, führen wir einfach dies aus

apt-get install postfix postfix-mysql postfix-doc mysql-client mysql-server courier-authdaemon courier-authlib-mysql courier-pop courier-pop-ssl courier-imap courier-imap-ssl postfix-tls libsasl2 libsasl2-modules libsasl2-modules-sql sasl2-bin libpam-mysql openssl phpmyadmin apache2 libapache2-mod-php5 php5 php5-mysql

Dir werden ein paar Fragen gestellt:

Create directories for web-based administration ? <-- No
General type of configuration? <-- Internet Site
Mail name? <-- server1.example.com
SSL certificate required <-- Ok

3 Anbringen des Quota Patchs in Postfix

Wir müssen die Postfix Quellen beziehen, sie mit dem Quota Patch patchen, ein neues Postfix .deb Paket bauen und diese .deb Pakete installieren:

apt-get install build-essential dpkg-dev fakeroot debhelper libgdbm-dev libldap2-dev libpcre3-dev libssl-dev libsasl2-dev postgresql-dev po-debconf dpatch libdb4.3-dev libmysqlclient15-dev


cd /usr/src
apt-get source postfix

(Pass auf, dass Du die richtige Postfix Version in den folgenden Befehlen verwendest. Ich habe Postfix 2.3.3 installiert. Du erfährst Deine Postfix Version indem Du dies ausführst

postconf -d | grep mail_version

)

wget http://web.onda.com.br/nadal/postfix/VDA/postfix-2.3.3-vda.patch.gz
gunzip postfix-2.3.3-vda.patch.gz
cd postfix-2.3.3
patch -p1 < ../postfix-2.3.3-vda.patch
dpkg-buildpackage
cd ..
dpkg -i postfix_2.3.3-1_i386.deb
dpkg -i postfix-mysql_2.3.3-1_i386.deb

4 Erstellen der MySQL Datenbank für Postfix/Courier

MySQL wird standardmäßig ohne Root Passwort installiert, was wir sofort ändern werden (ersetze yourrootsqlpassword mit dem Passwort Deine Wahl):

mysqladmin -u root password yourrootsqlpassword

Nun erstellen wir eine Datenbank mit der Bezeichnung mail:

mysqladmin -u root -p create mail

Als Nächstes gehen wir zu MySQL Kommandozeile:

mysql -u root -p

In der MySQL Kommandozeile erstellen wir den Benuzter mail_admin mit dem Passwort mail_admin_password (ersetze es mit Deinem Passwort), der SELECT,INSERT,UPDATE,DELETE Privilegien in der mail Datenbank hat. Diesen Benutzer verwenden Postfix und Courier, um sich mit der Mail Datenbank in Verbidung zu setzen:

GRANT SELECT, INSERT, UPDATE, DELETE ON mail.* TO 'mail_admin'@'localhost' IDENTIFIED BY 'mail_admin_password';
GRANT SELECT, INSERT, UPDATE, DELETE ON mail.* TO 'mail_admin'@'localhost.localdomain' IDENTIFIED BY 'mail_admin_password';
FLUSH PRIVILEGES;

Immer noch in der MySQL Kommandozeile erstellen wir die Tabellen, die Postfix und Courier benötigen:

USE mail;


CREATE TABLE domains (
domain varchar(50) NOT NULL,
PRIMARY KEY (domain) )
TYPE=MyISAM;

CREATE TABLE forwardings (
source varchar(80) NOT NULL,
destination TEXT NOT NULL,
PRIMARY KEY (source) )
TYPE=MyISAM;

CREATE TABLE users (
email varchar(80) NOT NULL,
password varchar(20) NOT NULL,
quota INT(10) DEFAULT '10485760',
PRIMARY KEY (email)
) TYPE=MyISAM;

CREATE TABLE transport (
domain varchar(128) NOT NULL default '',
transport varchar(128) NOT NULL default '',
UNIQUE KEY domain (domain)
) TYPE=MyISAM;

quit;

Wie Dir vielleicht aufgefallen ist, haben wir mit dem quit; Befehl die MySQL Kommandozeile verlassen und befinden uns wieder in der Linux Kommandozeile.

Die domains Tabelle speichert jede virtuelle Domain, für die Postfix E-Mails erhalten soll (z.B. example.com).
domain
example.comDie forwardings Tabelle ist für das Aliasing einer E-Mail Adresse mit der anderen zustänidg, z.B. leitet E-Mails für info@example.com an sales@example.com weiter.
source destination
info@example.com sales@example.comDie users Tabelle speichert alle virtuellen Benutzer (das heißt E-Mail Adressen, da die Adressen und der Benutzername das Gleiche ist) und Passwörter (in verschlüsselter Form!) sowie einen Quota-Wert für jede Mail Box (in diesem Beispiel ist der Standardwert 10485760 bytes, das heißt 10MB).
email password quota
sales@example.com No9.E4skNvGa. ("secret" in encrypted form) 10485760Die transport Tabelle ist optional, sie ist für fortgeschrittene Benutzer. Sie erlaubt Mails an einzelne Benutzer, ganze Domains oder alle Mails an einen anderen Server weiterzuleiten. Zum Beispiel würde
domain transport
example.com smtp:[1.2.3.4]alle E-Mails für example.com via smtp Protokoll an den Server mit der IP Adresse 1.2.3.4 weiterleiten (die eckigen Klammern [] bedeuten "schlage den MX DNS Record nicht nach" (was für IP Adressen Sinn macht…). Wenn Du stattdessen einen Fully Qualified Domain Name (FQDN) nutzt, verwendest Du die eckigen Klammern nicht.).

Übrigens (ich gehe davon aus, dass die IP Adresse Deines Mail Server System 192.168.0.100 ist), kannst Du auf phpMyAdmin über http://192.168.0.100/phpmyadmin/ in einem Browser zugreifen und Dich als mail_admin anmelden. Dann kannst Du Dir die Datenbank ansehen. Späer kannst Du phpMyAdmin verwenden, um Deinen Mail Server zu verwalten.

5 Konfiguration von Postfix

Nun müssen wir Postfix mitteilen, wo es alle Informationen in der Datenbank finden kann. Dafür müssen wir sechs Textdateien erstellen. Du wirst feststellen, dass ich Postfix mitteile, sich mit MySQL auf der IP Adresse 127.0.0.1 anstelle von localhost zu verbinden. Postfix läuft in einem Chroot Gefängnis und hat keinen Zugriff auf den MySQL Socket welchen er versuchen würde zu verbinden, wenn ich Postfix mitgeteilt hätte, localhost zu verwenden. Wenn ich 127.0.0.1 verwende, nutzt Postfix den TCP Netzwerkbetrieb um sich mit MySQL zu verbinden, was auch im Chroot Gefängnis kein Problem darstellt (die Alternative wäre den MySQL Socket in ein Chroot Gefängnis zu verschieben, was wieder andere Probleme verursacht).

Bitte pass auf, dass /etc/mysql/my.cnf folgende Zeile enthält:

vi /etc/mysql/my.cnf


[...]
bind-address = 127.0.0.1 [...]
Wenn Du /etc/mysql/my.cnf modifizieren musstest, dann starte MySQL jetzt neu:

/etc/init.d/mysql restart

Führe dies aus

netstat -tap

um sicher zu gehen, dass MySQL auf 127.0.0.1 (localhost.localdomain) hört:

root@server1:/usr/src# netstat -tap
Active Internet connections (servers and established)
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
tcp 0 0 localhost.localdo:mysql *:* LISTEN 4556/mysqld
tcp 0 0 *:smtp *:* LISTEN 12994/master
tcp6 0 0 *:imaps *:* LISTEN 4816/couriertcpd
tcp6 0 0 *:pop3s *:* LISTEN 4263/couriertcpd
tcp6 0 0 *:pop3 *:* LISTEN 4198/couriertcpd
tcp6 0 0 *:imap2 *:* LISTEN 4761/couriertcpd
tcp6 0 0 *:www *:* LISTEN 13283/apache2
tcp6 0 0 *:ssh *:* LISTEN 3192/sshd

Lass uns nun unsere sechs Textdateien erstellen.

vi /etc/postfix/mysql-virtual_domains.cf


user = mail_admin
password = mail_admin_password dbname = mail query = SELECT domain AS virtual FROM domains WHERE domain='%s' hosts = 127.0.0.1

vi /etc/postfix/mysql-virtual_forwardings.cf


user = mail_admin
password = mail_admin_password dbname = mail query = SELECT destination FROM forwardings WHERE source='%s' hosts = 127.0.0.1

vi /etc/postfix/mysql-virtual_mailboxes.cf


user = mail_admin
password = mail_admin_password dbname = mail query = SELECT CONCAT(SUBSTRING_INDEX(email,'@',-1),'/',SUBSTRING_INDEX(email,'@',1),'/') FROM users WHERE email='%s' hosts = 127.0.0.1

vi /etc/postfix/mysql-virtual_email2email.cf


user = mail_admin
password = mail_admin_password dbname = mail query = SELECT email FROM users WHERE email='%s' hosts = 127.0.0.1

vi /etc/postfix/mysql-virtual_transports.cf


user = mail_admin
password = mail_admin_password dbname = mail query = SELECT transport FROM transport WHERE domain='%s' hosts = 127.0.0.1

vi /etc/postfix/mysql-virtual_mailbox_limit_maps.cf


user = mail_admin
password = mail_admin_password dbname = mail query = SELECT quota FROM users WHERE email='%s' hosts = 127.0.0.1
Ändere dann die Berechtigungen und die Gruppe dieser Dateien:

chmod o= /etc/postfix/mysql-virtual_*.cf
chgrp postfix /etc/postfix/mysql-virtual_*.cf

Nun erstellen wir einen Benutzer und eine Gruppe mit der Bezeichnung vmail mit dem Home Verzeichnis /home/vmail. Dort werden alle Mail Boxen abgelegt.

groupadd -g 5000 vmail
useradd -g vmail -u 5000 vmail -d /home/vmail -m

Als Nächstes werden wir die Postfix Konfiguration vornehmen. Pass auf, dass Du server1.example.com mit einem gültigen FQDN ersetzt, sonst funktioniert Dein Postfix nicht richtig!

postconf -e 'myhostname = server1.example.com'
postconf -e 'mydestination = server1.example.com, localhost, localhost.localdomain'
postconf -e 'mynetworks = 127.0.0.0/8'
postconf -e 'virtual_alias_domains ='
postconf -e ' virtual_alias_maps = proxy:mysql:/etc/postfix/mysql-virtual_forwardings.cf, mysql:/etc/postfix/mysql-virtual_email2email.cf'
postconf -e 'virtual_mailbox_domains = proxy:mysql:/etc/postfix/mysql-virtual_domains.cf'
postconf -e 'virtual_mailbox_maps = proxy:mysql:/etc/postfix/mysql-virtual_mailboxes.cf'
postconf -e 'virtual_mailbox_base = /home/vmail'
postconf -e 'virtual_uid_maps = static:5000'
postconf -e 'virtual_gid_maps = static:5000'
postconf -e 'smtpd_sasl_auth_enable = yes'
postconf -e 'broken_sasl_auth_clients = yes'
postconf -e 'smtpd_recipient_restrictions = permit_mynetworks, permit_sasl_authenticated, reject_unauth_destination'
postconf -e 'smtpd_use_tls = yes'
postconf -e 'smtpd_tls_cert_file = /etc/postfix/smtpd.cert'
postconf -e 'smtpd_tls_key_file = /etc/postfix/smtpd.key'
postconf -e 'transport_maps = proxy:mysql:/etc/postfix/mysql-virtual_transports.cf'
postconf -e 'virtual_create_maildirsize = yes'
postconf -e 'virtual_mailbox_extended = yes'
postconf -e 'virtual_mailbox_limit_maps = proxy:mysql:/etc/postfix/mysql-virtual_mailbox_limit_maps.cf'
postconf -e 'virtual_mailbox_limit_override = yes'
postconf -e 'virtual_maildir_limit_message = "The user you are trying to reach is over quota."'
postconf -e 'virtual_overquota_bounce = yes'
postconf -e 'proxy_read_maps = $local_recipient_maps $mydestination $virtual_alias_maps $virtual_alias_domains $virtual_mailbox_maps $virtual_mailbox_domains $relay_recipient_maps $relay_domains $canonical_maps $sender_canonical_maps $recipient_canonical_maps $relocated_maps $transport_maps $mynetworks $virtual_mailbox_limit_maps'

Danach erstellen wir das SSL Zertifikat, das für TLS benötigt wird:

cd /etc/postfix
openssl req -new -outform PEM -out smtpd.cert -newkey rsa:2048 -nodes -keyout smtpd.key -keyform PEM -days 365 -x509

<-- Enter your Country Name (e.g., "DE").
<-- Enter your State or Province Name.
<-- Enter your City.
<-- Enter your Organization Name (e.g., the name of your company).
<-- Enter your Organizational Unit Name (e.g. "IT Department").
<-- Enter the Fully Qualified Domain Name of the system (e.g. "server1.example.com").
<-- Enter your Email Address.

Ändere dann die Berechtigungen des smtpd.key:

chmod o= /etc/postfix/smtpd.key

6 Konfiguration von Saslauthd

Führe zuerst Folgendes aus

mkdir -p /var/spool/postfix/var/run/saslauthd

Bearbeite dann /etc/default/saslauthd. Entferne das # vor START=yes und füge die Zeilen PARAMS="-m /var/spool/postfix/var/run/saslauthd -r" und PIDFILE="/var/spool/postfix/var/run/${NAME}/saslauthd.pid" hinzu. Die Datei sollte dann wie folgt aussehen:

vi /etc/default/saslauthd


# This needs to be uncommented before saslauthd will be run automatically
START=yes PARAMS="-m /var/spool/postfix/var/run/saslauthd -r" PIDFILE="/var/spool/postfix/var/run/${NAME}/saslauthd.pid" # You must specify the authentication mechanisms you wish to use. # This defaults to "pam" for PAM support, but may also include # "shadow" or "sasldb", like this: # MECHANISMS="pam shadow" MECHANISMS="pam"
Erstelle dann die Datei /etc/pam.d/smtp. Sie sollte lediglich folgende zwei Zeilen beinhalten (pass auf, dass Du die richtigen Datenbank Angaben eingibst):

vi /etc/pam.d/smtp


auth    required   pam_mysql.so user=mail_admin passwd=mail_admin_password host=127.0.0.1 db=mail table=users usercolumn=email passwdcolumn=password crypt=1
account sufficient pam_mysql.so user=mail_admin passwd=mail_admin_password host=127.0.0.1 db=mail table=users usercolumn=email passwdcolumn=password crypt=1
Erstelle als Nächstes die Datei /etc/postfix/sasl/smtpd.conf. So sollte sie aussehen:

vi /etc/postfix/sasl/smtpd.conf


pwcheck_method: saslauthd
mech_list: plain login allow_plaintext: true auxprop_plugin: mysql sql_hostnames: 127.0.0.1 sql_user: mail_admin sql_passwd: mail_admin_password sql_database: mail sql_select: select password from users where email = '%u'
Starte Postfix und Saslauthd dann neu:

/etc/init.d/postfix restart
/etc/init.d/saslauthd restart

7 Konfiguration von Courier

Nun müssen wir Courier mitteilen, dass es sich gegenüber unserer MySQL Datenbank authentifizieren soll. Bearbeite zunächst /etc/courier/authdaemonrc und ändere den Wert von authmodulelist so dass es heißt:

vi /etc/courier/authdaemonrc


[...]
authmodulelist="authmysql" [...]
Nimm dann ein Backup von /etc/courier/authmysqlrc vor und leere die alte Datei:

cp /etc/courier/authmysqlrc /etc/courier/authmysqlrc_orig
cat /dev/null > /etc/courier/authmysqlrc

Öffne dann /etc/courier/authmysqlrc und füge folgende Zeilen ein:

vi /etc/courier/authmysqlrc


MYSQL_SERVER localhost
MYSQL_USERNAME mail_admin MYSQL_PASSWORD mail_admin_password MYSQL_PORT 0 MYSQL_DATABASE mail MYSQL_USER_TABLE users MYSQL_CRYPT_PWFIELD password #MYSQL_CLEAR_PWFIELD password MYSQL_UID_FIELD 5000 MYSQL_GID_FIELD 5000 MYSQL_LOGIN_FIELD email MYSQL_HOME_FIELD "/home/vmail" MYSQL_MAILDIR_FIELD CONCAT(SUBSTRING_INDEX(email,'@',-1),'/',SUBSTRING_INDEX(email,'@',1),'/') #MYSQL_NAME_FIELD MYSQL_QUOTA_FIELD quota
Starte Courier dann neu:

/etc/init.d/courier-authdaemon restart
/etc/init.d/courier-imap restart
/etc/init.d/courier-imap-ssl restart
/etc/init.d/courier-pop restart
/etc/init.d/courier-pop-ssl restart

Indem Du dies ausführst

telnet localhost pop3

überprüfst Du, ob Dein POP3 Server richtig funktioniert. Es sollte +OK Hello there zurückgegeben werden. (Gib quit ein um zur Linux Kommandozeile zurückzukehren.)

root@server1:/etc/postfix# telnet localhost pop3
Trying 127.0.0.1...
Connected to localhost.localdomain.
Escape character is '^]'.
+OK Hello there.
quit
+OK Better luck next time.
Connection closed by foreign host.

8 Bearbeite /etc/aliases

Nun sollten wir /etc/aliases modifizieren und einen alias für postmaster darin festlegen. Du kannst eine Deiner vorhandenen E-Mail Adressen angeben, damit Du Benachrichtigungen an postmaster erhältst. Ändere außerdem die Root Zeile, damit Mails für Root an postmaster weitergeleitet werden:

vi /etc/aliases


# Added by installer for initial user
root: postmaster postmaster: postmaster@yourdomain.tld
Immer wenn Du /etc/aliases bearbeitest, musst Du dies danach ausführen

newaliases

und Postfix neu starten:

/etc/init.d/postfix restart


9 Installation von amavisd-new, SpamAssassin und ClamAV

Um amavisd-new, spamassassin und clamav zu installieren, führe diesen Befehl aus:

apt-get install amavisd-new spamassassin clamav clamav-daemon zoo unzip bzip2 unzoo libnet-ph-perl libnet-snpp-perl libnet-telnet-perl nomarch lzop pax

Danach müssen wir amavisd-new konfigurieren. Die Konfiguration ist auf verschiedene Dateien aufgesplittet, die sich im /etc/amavis/conf.d Verzeichnis befinden. Sieh Dir jede einzeln an um Dich mit der Konfiguration vertraut zu machen. Die meisten Einstellungen sind in Ordnung, allerdings müssen wir drei Dateien modifizieren:

First we must enable ClamAV and SpamAssassin in /etc/amavis/conf.d/15-content_filter_mode by uncommenting the @bypass_virus_checks_maps and the @bypass_spam_checks_maps lines:

vi /etc/amavis/conf.d/15-content_filter_mode

Die Datei sollte wie folgt aussehen:
use strict;
# You can modify this file to re-enable SPAM checking through spamassassin # and to re-enable antivirus checking. # # Default antivirus checking mode # Uncomment the two lines below to enable it back # @bypass_virus_checks_maps = ( %bypass_virus_checks, @bypass_virus_checks_acl, $bypass_virus_checks_re); # # Default SPAM checking mode # Uncomment the two lines below to enable it back # @bypass_spam_checks_maps = ( %bypass_spam_checks, @bypass_spam_checks_acl, $bypass_spam_checks_re); 1; # insure a defined return
Dann solltest Du Dir die Spam Einstellungen und die Aktionen für Spam-/Virus-Mails in /etc/amavis/conf.d/20-debian_defaults ansehen. Es besteht kein Grund irgendwas zu ändern, wenn die Standardeinstellungen für Dich in Ordnung sind. Die Datei beinhaltet viele Erklärungen, ich muss die Einstellungen hier also nicht näher erläutern:

vi /etc/amavis/conf.d/20-debian_defaults


$QUARANTINEDIR = "$MYHOME/virusmails";
$log_recip_templ = undef; # disable by-recipient level-0 log entries $DO_SYSLOG = 1; # log via syslogd (preferred) $syslog_ident = 'amavis'; # syslog ident tag, prepended to all messages $syslog_facility = 'mail'; $syslog_priority = 'debug'; # switch to info to drop debug output, etc $enable_db = 1; # enable use of BerkeleyDB/libdb (SNMP and nanny) $enable_global_cache = 1; # enable use of libdb-based cache if $enable_db=1 $inet_socket_port = 10024; # default listenting socket $sa_spam_subject_tag = '***SPAM*** '; $sa_tag_level_deflt = 2.0; # add spam info headers if at, or above that level $sa_tag2_level_deflt = 6.31; # add 'spam detected' headers at that level $sa_kill_level_deflt = 6.31; # triggers spam evasive actions $sa_dsn_cutoff_level = 10; # spam level beyond which a DSN is not sent $sa_mail_body_size_limit = 200*1024; # don't waste time on SA if mail is larger $sa_local_tests_only = 0; # only tests which do not require internet access? [...] $final_virus_destiny = D_DISCARD; # (data not lost, see virus quarantine) $final_banned_destiny = D_BOUNCE; # D_REJECT when front-end MTA $final_spam_destiny = D_BOUNCE; $final_bad_header_destiny = D_PASS; # False-positive prone (for spam) [...]
Bearbeite schließlich /etc/amavis/conf.d/50-user und füge die Zeile $pax='pax'; in der Mitte ein:

vi /etc/amavis/conf.d/50-user


[...]
$pax='pax'; [...]
Führe danach diese Befehle aus um den neuen clamav Benutzer der amavis Gruppe hinzuzufügen und starte amavisd-new und ClamAV neu:

adduser clamav amavis
/etc/init.d/amavis restart
/etc/init.d/clamav-daemon restart

Als Nächstes müssen wir die Konfigurationsdatei des Freshclam Daemons (das ist der Daemon, der regelmäßig und automatisch die neusten Virussignaturen von einem ClamAV Spiegel abruft) bearbeiten, da sie einen kleinen Fehler enthält. Öffne /etc/clamav/freshclam.conf und modifiziere die NotifyClamd Zeile, wie unten angezeigt wird:

vi /etc/clamav/freshclam.conf


[...]
NotifyClamd /etc/clamav/clamd.conf [...]
Then restart Freshclam (make sure no other Freshclam process (maybe of another ClamAV installation) is running because then our Freshclam will fail to start):

/etc/init.d/clamav-freshclam restart

Now we have to configure Postfix to pipe incoming email through amavisd-new:

postconf -e 'content_filter = amavis:[127.0.0.1]:10024'
postconf -e 'receive_override_options = no_address_mappings'

Afterwards append the following lines to /etc/postfix/master.cf:

vi /etc/postfix/master.cf


[...]
amavis unix - - - - 2 smtp -o smtp_data_done_timeout=1200 -o smtp_send_xforward_command=yes 127.0.0.1:10025 inet 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 -o receive_override_options=no_unknown_recipient_checks,no_header_body_checks -o smtpd_bind_address=127.0.0.1
Then restart Postfix:

/etc/init.d/postfix restart

Now run

netstat -tap

and you should see Postfix (master) listening on port 25 (smtp) and 10025, and amavisd-new on port 10024:

root@server1:/usr/local/sbin# netstat -tap
Active Internet connections (servers and established)
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
tcp 0 0 localhost.localdo:10024 *:* LISTEN 16043/amavisd (mast
tcp 0 0 localhost.localdo:10025 *:* LISTEN 15794/master
tcp 0 0 localhost.localdo:mysql *:* LISTEN 4783/mysqld
tcp 0 0 *:smtp *:* LISTEN 15794/master
tcp6 0 0 *:imaps *:* LISTEN 13452/couriertcpd
tcp6 0 0 *:pop3s *:* LISTEN 13517/couriertcpd
tcp6 0 0 *:pop3 *:* LISTEN 13480/couriertcpd
tcp6 0 0 *:imap2 *:* LISTEN 13412/couriertcpd
tcp6 0 0 *:www *:* LISTEN 4489/apache2
tcp6 0 0 *:ssh *:* LISTEN 3193/sshd

10 Install Razor, Pyzor And DCC And Configure SpamAssassin

Razor, Pyzor and DCC are spamfilters that use a collaborative filtering network. To install them, run

apt-get install razor pyzor dcc-client

Now we have to tell SpamAssassin to use these three programs. Edit /etc/spamassassin/local.cf and add the following lines to it:

vi /etc/spamassassin/local.cf


[...]
# dcc use_dcc 1 dcc_path /usr/bin/dccproc dcc_add_header 1 dcc_dccifd_path /usr/sbin/dccifd #pyzor use_pyzor 1 pyzor_path /usr/bin/pyzor pyzor_add_header 1 #razor use_razor2 1 razor_config /etc/razor/razor-agent.conf #bayes use_bayes 1 use_bayes_rules 1 bayes_auto_learn 1
Restart amavisd-new afterwards:

/etc/init.d/amavis restart


11 Quota Exceedance Notifications

If you want to get notifications about all the email accounts that are over quota, then do this:

cd /usr/local/sbin/
wget http://puuhis.net/vhcs/quota.txt
mv quota.txt quota_notify
chmod 755 quota_notify

Open /usr/local/sbin/quota_notify and edit the variables at the top. Further down in the file (towards the end) there are two lines where you should add a % sign:

vi /usr/local/sbin/quota_notify


[...]
my $POSTFIX_CF = "/etc/postfix/main.cf"; my $MAILPROG = "/usr/sbin/sendmail -t"; my $WARNPERCENT = 80; my @POSTMASTERS = ('postmaster@yourdomain.tld'); my $CONAME = 'My Company'; my $COADDR = 'postmaster@yourdomain.tld'; my $SUADDR = 'postmaster@yourdomain.tld'; my $MAIL_REPORT = 1; my $MAIL_WARNING = 1; [...] print "Subject: WARNING: Your mailbox is $lusers{$luser}% full.n"; [...] print "Your mailbox: $luser is $lusers{$luser}% full.nn"; [...]
Run

crontab -e

to create a cron job for that script:
0 0 * * * /usr/local/sbin/quota_notify &> /dev/null
(Note (a little off-topic): on Ubuntu crontab -e will automatically open the editor nano. If you are used to working with the editor vi (like me), run the following commands:

rm -f /etc/alternatives/editor
ln -s /usr/bin/vi /etc/alternatives/editor

Afterwards, run crontab -e, and vi will come up.)

12 Test Postfix

To see if Postfix is ready for SMTP-AUTH and TLS, run

telnet localhost 25

After you have established the connection to your Postfix mail server type

ehlo localhost

If you see the lines

250-STARTTLS

and

250-AUTH

everything is fine:

root@server1:/usr/local/sbin# telnet localhost 25
Trying 127.0.0.1...
Connected to localhost.localdomain.
Escape character is '^]'.
220 server1.example.com ESMTP Postfix (Ubuntu)
ehlo localhost
250-server1.example.com
250-PIPELINING
250-SIZE 10240000
250-VRFY
250-ETRN
250-STARTTLS
250-AUTH LOGIN PLAIN
250-AUTH=LOGIN PLAIN
250-ENHANCEDSTATUSCODES
250-8BITMIME
250 DSN
quit
221 2.0.0 Bye
Connection closed by foreign host.
root@server1:/usr/local/sbin#

Type

quit

to return to the system shell.

13 Populate The Database And Test

To populate the database you can use the MySQL shell:

mysql -u root -p
USE mail;

At least you have to create entries in the tables domains and users:

INSERT INTO `domains` (`domain`) VALUES ('example.com');
INSERT INTO `users` (`email`, `password`, `quota`) VALUES ('sales@example.com', ENCRYPT('secret'), 10485760);

(Please take care you use the ENCRYPT syntax in the second INSERT statement in order to encrypt the password!)

If you want to make entries in the other two tables, that would look like this:

INSERT INTO `forwardings` (`source`, `destination`) VALUES ('info@example.com', 'sales@example.com');
INSERT INTO `transport` (`domain`, `transport`) VALUES ('example.com', 'smtp:mail.example.com');

To leave the MySQL shell, type

quit;

For most people it is easier if they have a graphical front-end to MySQL; therefore you can also use phpMyAdmin (in this example under http://192.168.0.100/phpmyadmin/ or http://server1.example.com/phpmyadmin/) to administrate the mail database. Again, when you create a user, go sure that you use the ENCRYPT function to encrypt the password:


I do not think I have to explain the domains and users table further.

The forwardings table can have entries like the following:
source destination  
info@example.com sales@example.com Redirects emails for info@example.com to sales@example.com
@example.com thomas@example.com Creates a Catch-All account for thomas@example.com. All emails to example.com will arrive at thomas@example.com, except those that exist in the users table (i.e., if sales@example.com exists in the users table, mails to sales@example.com will still arrive at sales@example.com).
@example.com @anotherdomain.tld This redirects all emails to example.com to the same user at anotherdomain.tld. E.g., emails to thomas@example.com will be forwarded to thomas@anotherdomain.tld.
info@example.com sales@example.com, billing@anotherdomain.tld Forward emails for info@example.com to two or more email addresses. All listed email addresses under destination receive a copy of the email.The transport table can have entries like these:
domain transport  
example.com : Delivers emails for example.com locally. This is as if this record would not exist in this table at all.
example.com smtp:mail.anotherdomain.tld Delivers all emails for example.com via smtp to the server mail.anotherdomain.com.
example.com smtp:mail.anotherdomain.tld:2025 Delivers all emails for example.com via smtp to the server mail.anotherdomain.com, but on port 2025, not 25 which is the default port for smtp.
example.com smtp:[1.2.3.4]
smtp:[1.2.3.4]:2025
smtp:[mail.anotherdomain.tld]
The square brackets prevent Postfix from doing lookups of the MX DNS record for the address in square brackets. Makes sense for IP addresses.
.example.com smtp:mail.anotherdomain.tld Mail for any subdomain of example.com is delivered to mail.anotherdomain.tld.
* smtp:mail.anotherdomain.tld All emails are delivered to mail.anotherdomain.tld.
joe@example.com smtp:mail.anotherdomain.tld Emails for joe@example.com are delivered to mail.anotherdomain.tld.See

man transport

for more details.

Please keep in mind that the order of entries in the transport table is important! The entries will be followed from the top to the bottom.

Important: Postfix uses a caching mechanism for the transports, therefore it might take a while until you changes in the transport table take effect. If you want them to take effect immediately, run

postfix reload

after you have made your changes in the transport table.

14 References

15 Links