user: pass:
Howto für Postfix mit Cyrus-imap / POP und SMTP-Auth

Ergänzend zu zu dem HowTo welches ich bereits zu Postfix geschrieben habe, möchte ich nun noch beschreiben wie es auf relativ einfache Art-
und Weise möglich ist einen komplett dynamischen Mailserver aufzubauen.
Als Zusatz kommt dieses Mal noch der Spamassassin hinzu, da wir ja mitlerweile immer mehr mit den unerwünschten Werbungen bombadiert werden.


Als Grundlage nehmen wir, wie auch schon zuvor ein Debian Sarge. Hier installieren wir zunächst folgende Packete mit dem Tool Apt

> apt-get install postfix postfix-tls postfix-mysql cyrus-admin cyrus-common cyrus-imapd cyrus-pop3d mysql-server mysql-common apache apache-common apache-utils php4 php4-mysql php4-imap php4-pear libpam-mysql sasl-bin libsasl-modules libsasl-dev

Hier eine kurze Erklärung zu dem installierten Programmen/Libs

postfix - Sollte klar sein, schließlich wollen wir einen Mailserver betreiben. Ihr werdet vermutlich gefragt ob exim deinstalliert werden
soll, einfach ja sagen.

cyrus - Wie wir schon in der Überschrift sehen, wollen wir ja Postfix mit cyrus-imap und cyrus-pop3d installieren.

mysql - Um die Benutzer und Zugriffsrechte etc. über MYSQL verwalten zu können, muss natürlich auch der entsprechende Datenbankserver
installiert sein. Wenn Ihr selber noch die Clients von MYSQL benötigt, dann könnt Ihr noch das Paket "mysql-client" installieren.

php4 - Das ist kein Muss, aber wenn man hinterher mit dem Webfrontend "web-cyradm" arbeiten will, dann ist das von nöten. Wer lieber mit
dem Consolentool "cyradm" arbeitet, braucht weder php4 noch den Apache Webserver, dazu aber später mehr. Im übrigen könntet Ihr dann auch die
sasldb nutzen, ist vielleicht nicht so "overkill" wie mysql ;)

apache - Das sollte klar sein, wenn nicht dann schließt an dieser Stelle das Howto.

libpam-mysql - Hiermit kann man sich über die Datenbank authentifizieren, das was normalerweise über die Shadow / pwcheck etc. macht,
übernimmt nun unser pwcheck auf das pam-mysql Modul.

Die ist natürlich nur eine kleine Erklärung, denn man muss ja nicht übertreiben. Nachdem die Programme installiert sind, stoppen wir erstmal
die ganzen Dienste, damit wir diese in Ruhe konfigurieren können.

> /etc/init.d/postfix stop ;/etc/init.d/mysql stop ;/etc/init.d/apache stop

Jetzt legen wir mal mit der Konfiguration los. Da bei mir das System nun schon produktiv läuft und ich eigentlich zu faul bin das ganze jetzt noch einmal zu installieren, kann es sein das ich das ein oder andere vergesse.
Fall Ihr Probleme habt, dann schickt mir bitte eine Mail an henrik@3-freun.de, ich werde euch dann schnellstmöglich helfen.

Wir fangen mit der main.cf vom Postfix an.

--snip--
## Das sind die Standartpfade von Postfix.
command_directory = /usr/sbin
daemon_directory = /usr/lib/postfix
program_directory = /usr/lib/postfix

## Euer Mailserver wird sich mit dieser Zeile melden. $myhostname wird durch den nachfolgenden Eintrag
## gesetzt. Ihr könnt die Variable auch ersetzen durch einen festen Wert. $mailname wird durch /etc/mailname ersetzt,
## auch hier kann ein fester Wert eingefügt werden. Die Werte in der Klammer könnt Ihr ebenfalls setzen. Hier bietet sich z.B. an
## (SMTP main.mailserver.de Administrative contact: eure@mail.addy)
smtpd_banner = $myhostname ESMTP $mail_name (Mailserver)
setgid_group = postdrop
biff = no


## Legt hier euren Hostnamen an.
myhostname = mailserver.de

## Füge die Domain hinzu, welche der Mailserver nutzt. Dieses kann auch durch den MUA (Cyrus) gesetzt werden.
## Ob Ihr das also auf yes oder no setzt spielt hier keine große Rolle.
append_dot_mydomain = yes


## Ich glaube, hier muss ich nicht besonders drauf eingehen. Die Aliases sind Standart und liegen default-mäßig in /etc/.
## Ihr könnt auch die aliases in der chroot-Umgebung nutzen. Es läuft beides, jedoch empfehle ich euch das Ihr die Standarteinstellungen
## stehen lasst.
alias_maps = hash:/etc/aliases
alias_database = hash:/etc/aliases
transport_maps = hash:/etc/postfix/transport

## Hierzu gibt es nur wenig zu sagen.
myorigin = /etc/mailname

## Jetzt kommen wir wieder zur "destination". Die Einträge erklären sich eigentlich von selber.
mydestination = $myhostname, $mydomain, localhost.$mydomain
mynetworks = 127.0.0.0/8

## Hier kommen wir eigentlich zum interessanten Teil der Konfiguration.
## Der Transport findet also über "cyrus" statt. Die ganzen Maps werden über Mysql abgefragt, hierzu kommen wir aber noch
## später wenn wir die entsprechenden Dateien anlegen.
mailbox_transport = cyrus
virtual_maps = mysql:/etc/postfix/mysql-virtual.cf
sender_canonical_maps = mysql:/etc/postfix/mysql-canonical.cf
relay_domains = mysql:/etc/postfix/mysql-relay.cf
transport_maps = mysql:/etc/postfix/mysql-transport.cf

## Wie groß dürfen die Mailboxen sein? Unlimited... denn das Quota können wir nachher über den Cyrus setzen.
mailbox_size_limit = 0

## Für eine Extension (user+adress) setzen wir den nachvolgenden Parameter.
recipient_delimiter = +

## Da wir unseren SMTP ja auch mit ssl-Verschlüsselung nutzen wollen, benötigen wir auch folgende Parameter.
## Zunächst brauchen wir die Zertifikate. Hierfür sind die ersten 3 Einträge nötig.
## Der tls_random_source sagt eigentlich nur, woraus die Schlüssel generiert werden. SSL bringt hier in der Regel
## eigene Tools mit, aber das urandom-device hat sich bislang als sehr nützlich erwiesen.
smtpd_tls_cert_file = /etc/postfix/postfix.pem
smtpd_tls_key_file = /etc/postfix/postfix.pem
smtpd_tls_CAfile = /etc/postfix/postfix.pem
smtpd_tls_loglevel = 1
smtpd_tls_received_header = yes
smtpd_tls_session_cache_timeout = 3600s
tls_random_source = dev:/dev/urandom

## Da mit das mit den dummen Webemails doch so langsam auf den Senkel gegangen ist, habe ich eine weitere Einstellung
## vorgenommen, welche "RBL" vom Server einholt. relays.ordb.org ist eine der größten und meiner Meinung nach einer der besten
## realtime-black-lists. Wenn Ihr das Feature nicht nutzen wollt, dann lasst den Eintrag einfach raus, bzw. kommentiert Ihn aus.
maps_rbl_domains = relays.ordb.org
smtpd_client_restrictions = reject_maps_rbl

## Jetzt tätigen wir die einfachen SMTP-Einstellungen. Ich kommentiere diese nur ganz kurz und knapp, da die meisten sich eigentlich
## selber erklären.

# Wir möchten einen "ehlo $domain" erhalten wenn ein Client eine Email verschicken soll.
smtpd_helo_required = yes

# Schützen wir uns doch einfach vor Bruteforce-Attacken.
disable_vrfy_command = yes

# Wir aktivieren die "Restriction" welche wir hier setzen sofort... Man kann es unter Umständen auch disablen, wenn man sich nicht sicher
# ist, was man an dieser Stelle tut.
smtpd_delay_reject = yes

# Das gute alte SASL kommt zur Geltung.
smtpd_sasl_auth_enable = yes

# Für die Microsoftis mit Ihrem Outlook
broken_sasl_auth_clients = yes

# Bitte umbedingt leer lassen. Ihr müsst zur Zeit das Postfix aus dem Testing-Tree nutzen, damit dieser Parameter angenommen wird.
smtpd_sasl_local_domain =

# Mehr ist hier nicht ratsam ;) denn wir werden anschließend noch weitere Regeln einfügen.
smtpd_sasl_security_options = noanonymous

# Unser tolles Regelwerk. Wer noch mehr Optionen haben möchte, kann sich ja die Docs von sasl bzw. Postfix anschauen.
smtpd_recipient_restrictions =
permit_sasl_authenticated,
warn_if_reject, reject_unknown_client,
warn_if_reject, reject_unknown_hostname,
check_relay_domains,
reject

## Hierzu sei kurz was erklärt. Der Parameter "warn_if_reject" setzt uns einen Eintrag ins Logfile des Mailservers. Das ist sinnvoll,
## wenn Ihr neue Regel hinzufügt um den produktiven Email Verkehr nicht zu behindern. Wenn Ihr dann seht, dass diese Regeln auch nur an
## der Stelle zutreffen, wo Ihr diese haben wollt, dann könnt Ihr das "warn_if_reject" davor einfach rauslöschen und die Regel ist aktiv.

--snip--

Ihr könnt diese main.cf einfach kopieren und übernehmen. An den Stellen wo Ihr Ergänzungen eingeben müsst, ist es ja in der Datei beschrieben.



Gehen wir nun weiter im Text. In der main.cf haben wir ja bereits die Zeilen

--snip--
virtual_maps = mysql:/etc/postfix/mysql-virtual.cf
sender_canonical_maps = mysql:/etc/postfix/mysql-canonical.cf
relay_domains = mysql:/etc/postfix/mysql-relay.cf
transport_maps = mysql:/etc/postfix/mysql-transport.cf
--snip--

eingefügt. Diese Dateien existieren nach der normalen Installation noch nicht und müssen erst angelegt werden. Hierbei ist darauf zu achten,
das wir die Konfiguration entsprechend der Datenbank Einträge vornehmen. Wenn Ihr nachher nicht den web-cyradm nutzt, dann könnt Ihr die
Konfiguration entsprechend ändern. Ich habe es so laufen, halte den Weg aber für sehr kompliziert und Ihr solltet schon wissen was Ihr tut.

Ich gebe euch daher nur die Anleitung für den standart web-cyradm, damit euer System nachher auch funktioniert ;)

Bei allen Dateien gilt folgendes:
hosts = Datenbank-server
user = Benutzer der auf die DB zugreifen darf
password = Passwort für den DB-User
dbname = Der Name der DB in dem die Einstellungen gespeichert werden.
table = Die Tabelle in der nachgeschaut werden soll.
select_field = Das Feld der Tabelle in dem der Wert stehen soll

Bei einigen Dateien gibt es hierzu noch Ergänzungen in Form von:
additional_conditions = Um die DB Abfrage einzuschränken. Z.B. select * from alias where status = 1

Gehen wir mal von oben nach unten durch und richten zunächst die Datei mysql-virtual.cf ein.
--snip mysql-virtual.cf--
hosts = localhost
user = benutzer
password = passwort
dbname = datenbankname
table = virtual
select_field = dest
where_field = alias
additional_conditions = and status = '1'
--snip--

--snip mysql-canonical.cf--
hosts = localhost
user = benutzer
password = passwort
dbname = datenbankname
table = virtual
select_field = alias
where_field = username
additional_conditions = and status = '1' limit 1
--snip--

--snip mysql-relay.cf--
hosts = localhost
user = benutzer
password = passwort
dbname = datenbankname
table = domain
select_field = domain_name
where_field = prefix
--snip--

--snip mysql-transport.cf--
hosts = localhost
user = benutzer
password = passwort
dbname = datenbankname
table = domain
select_field = transport
where_field = domain_name
--snip--

Wenn diese Dateien angelegt sind und die Inhalte stimmen, dann seit Ihr auch schon fast fertig mit der Konfiguration. Es geht trotzdem
noch ein Stück weiter.

Die Datei /etc/pam.d/cyrus muss noch editiert werden. Hier gelten einfache Regeln :)

--snip /etc/pam.d/cyrus--
auth sufficient pam_mysql.so user=benutzer passwd=passwort host=localhost db=datenbankname table=accountuser usercolumn=username passwdcolumn=password crypt=1
auth sufficient pam_unix_auth.so

account required pam_mysql.so user=benutzer passwd=passwort host=localhost db=datenbankname table=accountuser usercolumn=username passwdcolumn=password crypt=1
account sufficient pam_unix_acct.so
--snip--

Die Zeilen machen eigentlich nichts besonderes und erklären sich fast von selber. Bei Fragen schaut einfach mal in /usr/share/doc/libpam-mysql
nach oder schreibt mich an. Wichtig ist hier, daß die Benutzer und Passwörter mit dennen aus den Postfix-mysql-Dateien übereinstimmen.

Da wir uns über den pwcheck authentifizieren, der normale pwcheck aber kein mysql bzw. pam kennt, müssen wir den pwcheck "umlinken". Um nacher
den orginalzustand wiederherstellen zu können, löschen wir jedoch den alten pwcheck nicht sonder benennen Ihn einfach nur um.

> mv /usr/bin/pwcheck /usr/bin/pwcheck.old
> ln -s /usr/bin/pwcheck_pam /usr/bin/pwcheck

Jetzt steht nur noch aus, den Cyrus korrekt zu konfigurieren. Dazu nehmen wir uns die Datei /etc/imapd.conf vor.

--snip /etc/imapd.conf--
## Verzeichniss für die Konfiguration
configdirectory: /var/lib/cyrus

## Welche Partiotion nutzen wir für unseren Mailserver?
defaultpartition: default
partition-default: /var/spool/cyrus/mail

## Wir brauchen mindestens einen Admin-User. Bitte achtet drauf, daß dieser Benutzer keine Emails abrufen kann.
admins: cyrus

## Wollen wir mit jeder Mailbox ein automatisches Quota setzen? Ich nutze dieses Feature nicht, da ich das Quota auch speziell vergeben
## kann und meine Mailboxen in der Regel mehrere Hundert MB haben.
autocreatequota: 10000

## Lassen wir einen 8-Bit Zeichenheader in den Emails zu? Viele verstehen den Standart nicht, daher ignorieren wir das einfach mal,
## richtiger Weise müsste man jedoch dieses ausfiltern.
reject8bit: no

## Wollen wir die Benutzer bei überschreiten oder füllen des Quotas warnen? Ich halte das bei 90% für angemessen.
quotawarn: 90

## Gibt es einen Timeout für unsere Verbindungen?
timeout: 30

## Das selbe für POP3, nur das hier der Timeout nicht so hoch sein sollte.
poptimeout: 10

## Wir erlauben natürlich keine anonymous logins.
allowanonymouslogin: no

## Wieviel Zeit muss zwischen den Abrufintervallen bei POP3 sein? Ich halte 5 Minuten für angemessen und orientiere mich hier bei
## GMX
popminpoll: 5

## Welche "umask" also Beuntzerrechte haben die Cyrusprogramme?
umask: 077

--snip--

Da auf unserem Debiansystem ja der Postfix in einer chroot-Umgebung läuft, müssen wir Ihm die Möglichkeit geben auf den MySQL Sock zu
zugreifen. Dieses ist natürlich nur notwendig, wenn der Server mit den Datenbanken nicht extern läuft. Also kurz folgende Änderung
in der /etc/mysql/my.cnf tätigen:

[mysqld]
user = mysql
pid-file = /var/run/mysqld/mysqld.pid
- socket = /var/run/mysqld/mysqld.sock

[mysqld]
user = mysql
pid-file = /var/run/mysqld/mysqld.pid
+ socket = /var/spool/postfix/var/run/mysqld/mysqld.sock



Folgende Befehle müssen dann noch ausgeführt werden:

> mkdir -p /var/spool/postfix/var/run/mysqld
> chown mysql:root /var/spool/postfix/var/run/mysqld
> rm /var/run/mysqld
> ln -s /var/spool/postfix/var/run/mysqld /var/run/mysqld


Hey, wir nähern uns dem Ende dieser Dokumentation und euer Mailserver sollte mitlerweile schon funktionieren. Testen tun wir das jedoch
später, wir wollen ja erstmal die Möglichkeit haben Benutzer anzulegen. Wer jetzt die Benutzer via cyradm anlegen möchte, kann dieses tun.
Das könnte allerdings zu Problemen mit der MySQL Datenbank führen, da die Einstellungen nicht korrekt gespeichert werden, aber versucht
es halt ;) mehr dazu in man cyradm. Ach ja, wenn Ihr jetzt schon testen wollt, vergesst nicht die Datenbanken anzulegen ;)


Nun ladet Ihr euch am besten das Tool web-cyradm herunter. Damit das ganze dann auch professionell aufgebaut ist, legen wir hierfür auch
einen eigenen vhost im Apache an. Ich schlage vor das wir ein Verzeichniss /home/services gründen und dort die Daten einlegen.

> mkdir -p /home/service/web-cyradm
> cd /home/services/web-cyradm

Falls der Link nicht geht, dann ist eine neue Version von web-cyradm erschienen und Ihr solltet euch auf der Maintainer Seite die
aktuelle Adresse besorgen. http://www.web-cyradm.org

> wget http://www.web-cyradm.org//web-cyradm-0.5.4.tar.gz
> cd /home/services/web-cyradm
> tar xvfz web-cyradm-0.5.4.tar.gz
> mv webcyradm html
> chown -R www-data:www-data /home/services


> vi /etc/apache/httpd.conf

Hier fügt Ihr nun am besten an das Ende der Datei einen eigenen vhost für den Apache ein. Ich zeige euch einfach mal wie ich es gemacht habe.

--snip httpd.conf--

...

DocumentRoot /home/services/web-cyradm/html
ServerName webcyradm.euer.hostname.de
# ErrorLog logs/webcyradm.tux-shop.de-error.log
# CustomLog logs/webcyradm.tux-shop.de-custom.log common

...

--snip--

Wenn Ihr wollt, dann könnt Ihr das Logging aktiviert lassen, ich brauche es jedoch nicht mehr das bei mir die Sache läuft und ich eh
gegen Datenschrott bin ;) schließlich habe ich noch nen globales access-log und error-log, das sollte reichen.

Nun müsst Ihr noch die config.inc.php anpassen damit der web-cyradm auch funktioniert.

> cp /home/services/web-cyradm/html/config/conf.php.dist /home/services/web-cyradm/html/config/conf.php

--snip /home/services/web-cyradm/html/config/conf.php--

<?php

/* Die Sprache sollte eigentlich klar sei. Die locales findet Ihr ebenfalls im html Verzeichniss.
Der array teilt die Verbindungseingenschaften des Imapservers mit. Ihr könnt bzgl. des Benutzers ja nochmal
in eure /etc/imapd.conf schauen.
*/

$DEFAULTLANG = "de_DE";
$CYRUS = array(
'HOST' => 'HOST eures ImapServers',
'PORT' => 143,
'ADMIN' => 'Imap-Administrator',
'PASS' => 'Imap-Passwort'
);

/* Das hier sollte eigentlich auch klar sein, erinnert euch an die Eingaben die Ihr in den mysql-postfix-Dateien gesetzt habt.
Ihr könnt das natürlich auch über extern verwalten, d.h. der web-cyradm liegt auf einem anderem Rechner als der Imapserver,
daher ja auch die Angaben... klingt also logisch ;)
*/

$DB = array(
'TYPE' => 'mysql',
'USER' => 'Datenbankbenutzer',
'PASS' => 'Datenkbankpasswort',
'PROTO' => 'unix', // set to "tcp" for TCP/IP
'HOST' => 'localhost',
'NAME' => 'Datenbankname'
);

// Ab hier gibt es eigentlich nicht mehr viel zu erklären.

$DB['DSN'] = sprintf('%s://%s:%s@%s+%s/%s', $DB['TYPE'], $DB['USER'],
$DB['PASS'], $DB['PROTO'],
$DB['HOST'], $DB['NAME']);

/* Das müsst Ihr noch anlegen und dem www-data:www-data die Rechte für das Verzeichniss geben. Die Einträge könnt Ihr selber
bestimmen die dort gesetzt werden. Dazu verändert einfach die Variable "error_reporting" mehr dazu steht aber in der orginal-conf.php
*/

$LOG_DIR = "/var/log/web-cyradm/";

$SESS_TIMEOUT = 1000;

$DEFAULT_QUOTA = 20000;

$CRYPT = "crypt";

$DOMAIN_AS_PREFIX = 0;

$PASSWORD_CHANGE_METHOD = "sql";

error_reporting(E_ERROR);

$VERSION="0.5.4";

$RESERVED="postmaster,root";

--snip--

Wow, jetzt nur noch die Datenbanken anlegen und schon sollte alles passen ;)

web-cyradm bringt fertige SQL-Dumps mit, die wir eigentlich nur noch einpflegen müssen. Diese liegen im html/scripts Ordner. Interessant
sind hier eigentlich nur die zwei mysql-Dateien.
Dazu einfach mal den Import machen ;O)
Ahh... bevor ich es vergesse, ich mysql könnte auch kein Passwort haben, wenn Ihr also eine Zugriffsverletzung auf den Datenbankserver
erhaltet, lasst das -p einfach mal weg. Aber setzt früher oder später bitte ein Passwort, keiner sollte einfach so Zugriff auf Eure
Datenbanken haben. Dazu könnt Ihr den mysqladmin nutzen oder das Tool mysql (welches ich bevorzuge). Dem Ein- oder Anderem wird sichlich
auch phpMyAdmin ein Begriff sein, auch hiermit kann man die Passwörter setzen aber das schweift jetzt zu weit aus.


Hier wird der Benutzer "mail" angelegt. Er erhält das Passwort secret, ich würde das an eurer Stelle im MySQL-Dump ändern, am besten direkt
auf das was Ihr euch zuvor schon ausgesucht habt. Auch muss hier die Datenbank auf das geändert werden, was Ihr in den Postfixdateien
eingestellt habt. Auch die Datenbank "mail" wird angelegt, das müsstet Ihr sinnvollerweise auch auf das Abändern was Ihr bisher als DB-Name
verwendet habt.

> mysql -u root -p < /usr/share/webcyradm/scripts/insertuser_mysql.sql
> mysql -u root -p mail < /usr/share/webcyradm/scripts/insertuser_mysql.sql

Der zweite Dump erzeugt die Datenbanken mit dennen der web-cyradm arbeiten wird. Gleichzeitig wird hier ein Benutzer "admin" angelegt welchem das Passwort "test" vergeben wird. Damit könnt Ihr euch nachher auf der web-cyradm Oberfläche anmelden.

Damit wir nun auch noch sehen was passiert, ändern wir in der /etc/postfix/master.cf noch fix die Zeile

--snip--
...
smtp inet n - - - - smtpd
...
--snip--
nach
--snip--
...
smtp inet n - - - - smtpd -v
...
--snip--
ab.

Dieser Eintrag erzeug ein verbose-Logging in /var/log/mail.*

Nun starten wir unsere Dienste wieder mit

> /etc/init.d/postfix start;/etc/init.d/apache start;/etc/init.d/mysql start


Anschließend
> tail -f /var/log/mail.info

Fertig ;)

Nun melden wir uns über die Oberfläche web-cyradm an.

http://webcyradm.euer.hostname.de

Anmelden, Domain einrichten, Benutzer anlegen und eine Testmail schicken. Es sollte soweit alles funktionieren, wenn nicht --->>> Mail ME ;)


Ich hoffe euch weitergeholfen zu haben und freue mich natürlich über Kritik und/oder Anregungen zu dieser Anleitung. Berichtet mir doch
einfach eure Erfolge. Vielleicht habt Ihr noch Ergänzungen? Was kann man besser machen? Immer nur her damit.

Grüße Henrik Hasenkamp henrik@3-freun.de