当前位置:Linux教程 - Email - email - CNGNU Postfix邮件系统系列指南之一0.52

email - CNGNU Postfix邮件系统系列指南之一0.52

CNGNU Postfix邮件系统系列指南之一0.52
2004-04-23 15:18 pm
来自:Linux文档
现载:Www.8s8s.coM
地址:无名

Postfix + Cyrus-IMAP + Cyrus-SASL + MySQL + IMP完全指南

CNGNU Postfix邮件系统系列指南之一

Postfix + Cyrus-IMAP + Cyrus-SASL + MySQL + IMP
完全指南


 

作者:王兴宇 <[email protected]>

版本:0.52

版权:GPL

发布日期:2003-12-02

 

目录

1.  概述

1.1.  目的

1.2.  更新历史

1.3.  TODO

1.4.  鸣谢

2.  系统功能

3.  系统基本前提

4.  配置MySQL

4.1.  运行

4.2. 测试

4.3.  配置

5.  安装pam_mysql

5.1.  下载

5.2.  编译与安装

5.3.  配置

6.  安装Cyrus-SASL

6.1.  下载

6.2.  编译与安装

6.3.  配置

6.4. 运行

7.  安装Postfix

7.1.  下载

7.2.  编译与安装

7.3.  配置

7.4.  运行

7.5.  测试

8.  安装Cyrus-IMAP

8.1.  下载

8.2.  编译与安装

8.3.  配置

8.4.  运行

8.5.  测试

9.  安装IMP

9.1.  下载

9.2.  配置Apache/PHP

9.3.  配置Horde

9.4.  配置Imp

9.5.  配置Turba

9.6.  测试IMP

10.  其它

10.1.  启动脚本

10.2.  整体测试


 

1.  概述

1.1.  目的

  本文试图介绍如何在一个Linux平台上安装一套功能完整的邮件系统。这里我们以Postfix做SMTP服务器、Cyrus-IMAP做POP3/IMAP4服务器、通过Cyrus-SASL对存储在MySQL数据库中的用户进行验证和授权,并且使用IMP来提供一个完善的WEBMAIL界面。

  这个邮件系统的设计目标是提供一个可扩充的、具备大多数功能的邮件系统。

  本文的最新版本可以在这里找到:http://www.cngnu.org/technology/Postfix_I.html

  有关本文所涉及的技术问题,请到http://www.anti-spam.org.cn/forums/的mail版讨论,我会尽快回复的,请勿就技术问题给我发邮件。

  本文的版权遵循GPL,可以在不删除版权信息和注明修改的情况下任意传播。

1.2.  更新历史

  • 2002-05-21 第一次发布,版本0.20。
  • 2002-08-13 修正一些错误,版本0.21。
  • 2002-08-23 修正一些错误,版本0.22。
  • 2002-09-12 在RedHat Linux Advance Server V2.1上进行了测试,修正了一些错误,版本0.30。
  • 2002-12-12 修正了一些错误,添加了IMP部分的内容,版本0.31。
  • 2003-01-30 修正了一些错误,添加了非明文密码部分的内容,版本0.32。
  • 2003-02-05 修正了一些错误,版本0.33
  • 2003-03-26 使用了SASL V2和Cyrus-IMAP 2,支持使用db4的新的Linux发行版,如RedHat 8.0和Mandrake 9.0,并以RedHat 8.0为示范平台。修正了一些错误,版本0.40。
  • 2003-03-28 修正了一些错误,特别感谢bjchenxu,版本0.41。
  • 2003-09-24 添加了虚拟域功能,修正了一些笔误,版本0.50。
  • 2003-10-13 修正了虚拟域的错误,版本0.51。
  • 2003-12-02 修正了部分错误,版本0.52。如果没有其它的输入错误问题,本文将不再更新。

1.3.  TODO

  • 增加邮件列表功能
  • 增加SSL部分的内容
  • 翻译:希望有能力的朋友可以翻译这篇文章为英文,这样国外的朋友也可以看到

1.4.  鸣谢

  谢谢lesson.ward、Yunping Zhu、Temp、bjchenxu的指正。

 

  参考文档:http://www.delouw.ch/linux/Postfix-Cyrus-Web-cyradm-HOWTO/html/index.html。在这篇文章撰写之初,参考过该文章,目前该文章也在不断更新,大家也可以看看。

2.  系统功能

  系统逻辑结构:


+---------------------------------------------------+
|                                                   |
|  25/25    25/25     110/993  143/995    80/443    |
| Incoming Outgoing     POP3     IMAP    WEB-MAIL   |
|    /\       /\         /\       /\        /\      |
|    ||       ||         ||       ||        ||      |
|    \/       \/         \/       \/        \/      |
+-------------------+---------------+---------------+
|    Postfix        |               |      IMP      |
|                   |               +---------------+
|                   |      Cyrus-IMAP               |
|       +-----------+-------------------------------+
|       |                  Cyrus-SASL               |
|       +-------------------------------------------+
|       |                  saslauthd                |
|       +-------------------------------------------+
|       |                     PAM                   |
|       +-------------------------------------------+
|       |                  pam_mysql                |
+-------+-------------------------------------------+
|                      MySQL                        |
+---------------------------------------------------+

  整个系统对外的界面包括几个部分,用来发信的SMTP、用来收信的POP3和IMAP、以及一个WEB界面的邮件使用系统。这里没有提供WEB界面的管理工具,需要大家自行依据实际需要开发。

  MySQL作为系统中存储数据的核心,它存储了用户的信息。这个信息不但用于POP3/IMAP和SMTP AUTH的认证需要,而且也为Postfix提供了本地接收者的列表和转发功能。

  认证流程比较繁琐。整个认证是通过Cyrus-SASL来做的,通过运行一个守护进程saslauthd来监听认证需求。saslauthd这里使用了pam认证方式通过pam_mysql插件对MySQL数据库进行查找。

  系统为了支持虚拟域,所有的用户验证都用用户的邮件全称作为用户名,其实际的邮箱由于Postfix的限制,使用将邮件地址中“@”换成“~”的邮箱名。

3.  系统基本前提

  本文以Linux系统为目标平台,支持多数的Linux平台如RedHat 7.x/8.x、Mandrake 8.x/9.x等,理论上也会支持其他的Linux发行版,甚至其他的UNIX系统。

  这里以RedHat Linux V 8.0为说明平台。

  该说明平台除了基本的操作系统部分外,系统中还安装了如下的RPM:

  一、gcc:

    1.  gcc-3.2-7

    2.  gcc-c++-3.2-7

  二、db3:

    1.  db4-devel-4.0.14-14

    2.  db4-4.0.14-14

    3.  db4-utils-4.0.14-14

  三、pam:

    1.  pam-0.75-40

    2.  pam-devel-0.75-40

  四、mysql:

    1.  mysql-3.23.52-3

    2.  mysql-server-3.23.52-3

    3.  mysql-devel-3.23.52-3

  五、IMP相关:

    1. httpd-2.0.40-8

    2. httpd-devel-2.0.40-8

    2. gettext-0.11.4-3

    3. imap-devel-2001a-15

    4. krb5-libs-1.2.5-6

    5. krb5-devel-1.2.5-6

    6. openssl-0.9.6b-29

    7. openssl-devel-0.9.6b-29

  如果系统中没有,请自行安装RPM包或编译安装。除此之外,其他需要的部分将以源码方式编译。

4.  配置MySQL

4.1.  运行

  启动命令如下:

[root@mail root]# /etc/init.d/mysqld start

4.2.  测试

  启动MySQL后,首先检查日志/var/log/messages有无错误信息,然后检查进程,应该有如下进程存在:

[root@mail root]# pstree | grep mysqld

 

|-safe_mysqld---mysqld---mysqld---2*[mysqld]

 

  接着检查端口,应该有如下端口打开:

[root@mail root]# netstat -an | grep LISTEN

 

tcp  0  0 0.0.0.0:3306  0.0.0.0:*  LISTEN

 

4.3.  配置

  MySQL安装配置好以后,在MySQL中创建邮件用户数据库,并添加一个测试用户“[email protected]”,密码是“testpw”:

[root@mail root]# mysql mysql

Reading table information for completion of table and column names

You can turn off this feature to get a quicker startup with -A

 

Welcome to the MySQL monitor. Commands end with ; or \g.

Your MySQL connection id is 1 to server version: 3.23.52

 

Type 'help;' or '\h' for help. Type '\c' to clear the buffer.

 

mysql> CREATE DATABASE mail;

Query OK, 1 row affected (0.00 sec)

 

mysql> GRANT ALL ON mail.* TO mail@localhost

  -> IDENTIFIED BY "secret";

Query OK, 0 row affected (0.00 sec)

 

mysql> FLUSH PRIVILEGES;

Query OK, 0 row affected (0.00 sec)

 

mysql> USE mail;

Database changed

 

mysql> CREATE TABLE USER (

  -> USERNAME varchar(128) not null default '',

  -> PASSWORD varchar(64) not null default '',

  -> FORWARD varchar(128) not null default '',

  -> PATITION varchar(32) not null default 'default',

  -> QUOTE int not null default '1024',

  -> STATUS tinyint not null default '1');

Query OK, 0 rows affected (0.00 sec)

 

mysql> CREATE INDEX USER ON USER (USERNAME,PASSWORD,FORWARD,STATUS);

Query OK, 0 rows affected (0.00 sec)

Records: 0 Duplicates: 0 Warnings: 0

 

mysql> INSERT INTO USER (USERNAME,PASSWORD,FORWARD)VALUES

  -> ('[email protected]','$1$pi.WVgBx$a3dUCzBnbY76jnZlqWQCQ/','tester~cngnu.org');

Query OK, 1 row affected (0.01 sec)

 

mysql> \q

Bye

  上面的mail数据库的user表用来保存用户信息:

  • USERNAME和PASSWORD字段就是用户名和MD5-Crypt密码。这里采用了加密密码是为了更好的安全性。
  • FORWARD字段默认是指向用户的邮箱名的(邮箱名与用户的邮件地址全称类似,只是将“@”换成了“~”,参见下面Cyrus-IMAP部分描述),在此情况下,邮件递交到本地邮箱(由于Postfix区分邮箱的大小写,所以通过这样的一个转发,正好可以消除大小写的区别);如果FORWARD字段是另外一个用户名或者邮件地址,则该邮件被转发到别的用户或其它邮件地址。
  • STATUS字段用来指示该用户是否有效,可以通过修改该值为0来临时禁止某个用户。
  • 上面添加了一个邮件用户“[email protected]”,实际存储该用户的邮件在邮箱文件夹“cngnu~cngnu.org”中,它的密码是“testpw”,加密后的(MD5-CRYPT)密文是“$1$pi.WVgBx$a3dUCzBnbY76jnZlqWQCQ/”(可以通过系统的passwd命令来添加一个用户,生成密码,然后才/etc/shadow中复制。)

 

5.  安装pam_mysql

5.1.  下载

  http://sourceforge.net/projects/pam-mysql/

[root@mail root]# cd /usr/src

[root@mail src]# wget http://telia.dl.sourceforge.net/sourceforge/pam-mysql/pam_mysql-0.5.tar.gz

  注:如果不能访问该网站取得pam_mysql,请自行使用代理服务器访问。

5.2.  编译与安装

  编译pam_mysql:

[root@mail src]# tar -zxf pam_mysql-0.5.tar.gz

[root@mail src]# cd pam_mysql

  修改pam_mysql.c的源代码,去掉调试消息:

[root@mail pam_mysql]# vi +54 pam_mysql.c

  将如下一行:

#define DEBUG

  修改为:

/* #define DEBUG */

  然后编译:

[root@mail pam_mysql]# make

[root@mail pam_mysql]# cp pam_mysql.so /lib/security

 

  有些情况下,这个编译会报错,但是如果编译能生成pam_mysql.so模块,还是可以用的。

5.3.  配置

  创建/etc/pam.d/mail,它用来支持Cyrus-IMAP的imap认证、pop认证和Postfix的smtp认证:

[root@mail pam_mysql]# cd /etc/pam.d

[root@mail pam.d]# echo auth sufficient pam_mysql.so user=mail passwd=secret \

> host=localhost db=mail table=USER usercolumn=USERNAME passwdcolumn=PASSWORD \

> crypt=1 sqllog=0 > /etc/pam.d/mail

[root@mail pam.d]# echo account required pam_mysql.so user=mail passwd=secret \

> host=localhost db=mail table=USER usercolumn=USERNAME passwdcolumn=PASSWORD \

> crypt=1 sqllog=0 >> /etc/pam.d/mail

[root@mail pam.d]# echo auth sufficient pam_unix_auth.so >> /etc/pam.d/mail

[root@mail pam.d]# echo account sufficient pam_unix_acct.so >> /etc/pam.d/mail

  这里前面两行是指通过mysql数据库来认证用户,后面两行指是通过UNIX的基本方式认证用户(即系统用户)。这里我们之所以保留UNIX系统认证模式,是因为我们下面要通过系统用户cyrus来管理cyrus-imap邮箱。不过你也可以选择将这个管理帐号cyrus放入mysql认证数据库里面,只需要你在上面的数据库里面添加一个cyrus用户。

  通过给上面的crypt赋予不同的值可以使用多种密码存储方式:

  • crypt=0:表示使用明文来存储密码。这样存储的好处是简单,但是不够安全。
  • crypt=1:表示使用UNIX系统的DES加密密码方式来存储。即通常的UNIX的/etc/passwd(老式系统加密口令存储在这里)或/etc/shadow(较为新的系统加密口令存放在这里)中存储的加密口令。加密口令有两种,一种是普通的des加密的,也叫crypt(),这种密码是13位长,前面两个字符是加密种子;还有一种是使用了MD5算法增强了的,也叫MD5 crypt(),这种密码的加密种子是以$1$开头的12个字符,密码长度不定。
  • crypt=2:表示使用mysql的SQL函数password()加密方式来存储。
  • crypt=3:表示使用md5的散列方式来存储。这种方式和MD5 crypt()是不一样的。

  一般如果从系统用户迁移到使用数据库的虚拟用户时,可以使用crypt=1方式,系统会自动辨别两种加密口令。如果需要开发用户修改口令的功能时,C和Perl里面的crypt函数不能支持MD5 crypt()口令,需要使用额外的编程或模块来支持。

  做个符号链接/etc/pam.d/imap,它用来支持Cyrus-IMAP的imap认证:

[root@mail pam.d]# [ -f imap ] && mv imap imap.orig

[root@mail pam.d]# ln -s mail imap

  同样创建/etc/pam.d/pop ,它用来支持Cyrus-IMAP的pop3认证:

[root@mail pam.d]# [ -f pop ] && mv pop pop.orig

[root@mail pam.d]# ln -s mail pop

  同样创建/etc/pam.d/smtp ,它用来支持Postfix的smtp auth认证:

[root@mail pam.d]# [ -f smtp ] && mv smtp smtp.orig

[root@mail pam.d]# ln -s mail smtp

  系统上可能已经存在了这些文件,请将原来的改名或者删除。

6.  安装Cyrus-SASL

6.1.  下载

  http://asg.web.cmu.edu/cyrus/download/

[root@mail pam.d]# cd /usr/src

[root@mail src]# wget ftp://ftp.andrew.cmu.edu/pub/cyrus-mail/cyrus-sasl-2.1.15.tar.gz

6.2.  编译与安装

  编译Cyrus-sasl,只支持需要的plain和login认证方式:

[root@mail src]# tar -zxvf cyrus-sasl-2.1.15.tar.gz

[root@mail src]# cd cyrus-sasl-2.1.15

[root@mail cyrus-sasl-2.1.15]# ./configure --disable-sample \

> --disable-pwcheck --disable-cram --disable-digest \

> --disable-krb4 --disable-gssapi --disable-anon \

> --disable-otp \

> --with-saslauthd=/var/run/saslauthd \

> --enable-plain --enable-login

 

[root@mail cyrus-sasl-2.1.15]# make

[root@mail cyrus-sasl-2.1.15]# make install

 

[root@mail cyrus-sasl-2.1.15]# [ -d /usr/lib/sasl2 ] && mv /usr/lib/sasl2 /usr/lib/sasl2.orig

[root@mail cyrus-sasl-2.1.15]# ln -s /usr/local/lib/sasl2 /usr/lib/sasl2

  系统上如果已经安装了SASL 2,请先删除这些RPM或/usr/lib/sasl2这个目录。另外确保你的/usr/lib/sasl2目录中没有login和plain模块外的其他模块,否则容易导致认证失败。

 

  加载链接库:

[root@mail cyrus-sasl-2.1.15]# echo /usr/local/lib >> /etc/ld.so.conf

[root@mail cyrus-sasl-2.1.15]# echo /usr/local/lib/sasl2 >> /etc/ld.so.conf

[root@mail cyrus-sasl-2.1.15]# ldconfig

6.3.  配置

  设置Postfix使用SASL的saslauthd认证守护进程来支持smtp auth认证:

[root@mail cyrus-sasl-2.1.15]# echo pwcheck_method: saslauthd > /usr/lib/sasl2/smtpd.conf

    Cyrus-IMAP的SASL配置不使用标准的sasl语法,它的配置文件放在/etc/imapd.conf中,详细配置在Cyrus-IMAP部分说明。

6.4.  运行

  运行saslauthd守护进程,并使其使用pam认证模式来提供认证信息:

[root@mail cyrus-sasl-2.1.15]# /usr/local/sbin/saslauthd -a pam

  整个系统使用的认证机制比较复杂。所有的应用(SMTP、IMAP、POP3等)都采用SASL V2的saslauthd来认证;而saslauthd是通过它所支持的PAM模式来借助pam_mysql接口对存储在MySQL数据库中用户信息进行认证的。请参阅上面的系统结构以了解认证流程。

 

7.  安装Postfix

7.1.  下载

  http://www.postfix.org/ftp-sites.html

[root@mail cyrus-sasl-2.1.15]# cd /usr/src

[root@mail src]# wget http://postfix.energybeam.com/source/official/postfix-2.0.16.tar.gz

7.2.  编译与安装

  如果你的系统上原来有sendmail,先将其停止并将其文件改名:

[root@mail src]# /etc/init.d/sendmail stop

[root@mail src]# mv /usr/bin/newaliases /usr/bin/newaliases.orig

[root@mail src]# mv /usr/bin/mailq /usr/bin/mailq.orig

[root@mail src]# mv /usr/sbin/sendmail /usr/sbin/sendmail.orig

 

  然后添加两个组:postfix和maildrop和一个用户:postfix

[root@mail src]# groupadd -g 12345 postfix

[root@mail src]# groupadd -g 12346 postdrop

[root@mail src]# useradd -u 12345 -g 12345 -c postfix -M -d/no/where -s/no/shell postfix

  这里的组和用户的ID是系统中未使用的ID。

 

  编译Postfix,并支持mysql和sasl:

[root@mail src]# tar -xvzf postfix-2.0.16.tar.gz

[root@mail src]# cd postfix-2.0.16

 

[root@mail postfix-2.0.16]# make -f Makefile.init makefiles \

> 'CCARGS=-DUSE_SASL_AUTH -DHAS_MYSQL -I/usr/include/mysql -I/usr/local/include/sasl' \

> 'AUXLIBS=-L/usr/lib/mysql -L/usr/local/lib/sasl2 -lmysqlclient -lsasl2 -lz -lm'

[root@mail postfix-2.0.16]# make install

  安装时,安装程序会提问一些问题,可以直接按回车采用默认值。

  这里切记要专门指定你刚安装的SASL2的INCLUDE和LIB位置。由于现在很多linux发行版上都已经带有了sasl,如果不指定的话,很可能会使用了不同版本的头文件和库,在这种情况下,每次连接SMTP时,smtpd就会发生致命错误“Fatal: SASL per-connection server init...”而崩溃。

 

  修改系统的别名数据库位置:

[root@mail postfix-2.0.16]# cd /etc

[root@mail etc]# mv aliases aliases.orig

[root@mail etc]# ln -s postfix/aliases aliases

  给postfix用户做一个系统别名,并将超级用户的邮箱转发到一个普通用户如tester。使用/etc/postfix/aliases别名数据库:

[root@mail etc]# cd postfix

[root@mail postfix]# echo 'root: [email protected]' >> /etc/postfix/aliases

  生成/etc/postfix/aliases别名数据库:

[root@mail postfix]# postalias /etc/postfix/aliases

 

7.3.  配置

  修改/etc/postfix/master.cf中的关于cyrus的配置,(cyrus的命令行和以前有不兼容的地方,确保你的cyrus的参数如下使用了-r ${sender}参数):

[root@mail postfix]# vi master.cf

  将如下两行:

cyrus unix - n n - - pipe
 user=cyrus argv=/cyrus/bin/deliver -e -r ${sender} -m ${extension} ${user}

  修改为:

cyrus unix - n n - - pipe
 user=cyrus argv=/usr/cyrus/bin/deliver -e -r ${sender} -m ${extension} ${user}

  这里要把cyrus的路径修改为你的cyrus实际安装路径(我们下面会将cyrus-imap安装到/usr/cyrus)。 记着user=...这行前面是以空格缩进的。

 

[root@mail postfix]# vi main.cf

 

  修改/etc/postfix/main.cf的配置:

myhostname = mail.cngnu.org

mydomain = cngnu.org

myorigin = $mydomain

mydestination = $mydomain,$myhostname

 

alias_maps = hash:/etc/postfix/aliases

alias_database = hash:/etc/postfix/aliases

 

home_mailbox = Maildir/

 

mailbox_transport = cyrus

fallback_transport = cyrus

 

virtual_maps = hash:/etc/postfix/virtual,mysql:/etc/postfix/mysql-virtual.cf

 

smtpd_sasl_auth_enable = yes

smtpd_recipient_restrictions = permit_sasl_authenticated permit_auth_destination reject

broken_sasl_auth_clients = yes

smtpd_sasl_security_options = noanonymous

  在上面的配置文件里面使用了SASL来进行SMTP发信认证。

  如果希望支持更多的虚拟域,可以在mydestination参数后面加上你所要支持的域即可。

 

  创建/etc/postfix/mysql-virtual.cf,它提供了本地用户和邮件转发功能。FORWARD字段默认是指向用户的邮箱名的(邮箱名与用户的邮件地址全称类似,只是将“@”换成了“~”),此时邮件本地递交到用户邮箱:[email protected]里面;FORWARD是另外一个邮件地址或用户时,邮件转发到新的地址。此外,由于Postfix对于邮箱区别大小写,通过virtual功能的重写,可以保证大小写的邮件地址都可以正确接收。

[root@mail postfix]# vi mysql-virtual.cf

 

#

# mysql config file for alias lookups on postfix

#

 

# the user name and password to log into the mysql server

hosts = localhost

user = mail

password = secret

 

# the database name on the servers

dbname = mail

 

# the table name

table = USER

 

select_field = FORWARD

where_field = USERNAME

additional_conditions = and STATUS = '1' limit 1

 

  创建上面指定的/etc/postfix/virtual的DB库:

[root@mail postfix]# postmap virtual

  保留db格式的virtual库是为了系统添加一些虚拟域和转发方便起见。

7.4.  运行

  启动命令如下:

[root@mail postfix]# /usr/sbin/postfix start

7.5.  测试Postfix

  启动Postfix后,首先检查日志/var/log/messages有无错误信息,然后检查进程,应该有如下进程存在:检查端口及进程:

[root@mail postfix]# pstree |grep master

 

|-master-+-pickup

 

  接着检查端口,应该有如下端口打开:

[root@mail postfix]# netstat -an |grep LISTEN

 

tcp  0  0 0.0.0.0:25  0.0.0.0:*  LISTEN

 

  再检测SMTP服务是否正常:

[root@mail postfix]# telnet localhost 25

Trying 127.0.0.1...
Connected to localhost.
Escape character is '^]'.
220 mail.cngnu.org ESMTP Postfix
QUIT
221 Bye
Connection closed by foreign host.

  使用如下命令测试postfix的SMTP的认证:

  PLAIN认证方式:

[root@mail postfix]# perl -MMIME::Base64 -e \

> 'print encode_base64("tester\@cngnu.org\0tester\@cngnu.org\0testpw");'
dGVzdGVyQGNuZ251Lm9yZwB0ZXN0ZXJAY25nbnUub3JnAHRlc3Rwdw==

 

[root@mail postfix]# telnet localhost 25

Trying 127.0.0.1...
Connected to localhost.
Escape character is '^]'.
220 mail.cngnu.org ESMTP Postfix

EHLO cngnu

250-mail.cngnu.org

250-PIPELINING

250-SIZE 10240000

250-VRFY

250-ETRN

250-AUTH LOGIN PLAIN

250-AUTH=LOGIN PLAIN

250-XVERP

250 8BITMIME

AUTH PLAIN dGVzdGVyQGNuZ251Lm9yZwB0ZXN0ZXJAY25nbnUub3JnAHRlc3Rwdw==

235 Authentication successful

QUIT

221 Bye

Connection closed by foreign host.

  LOGIN认证方式:

[root@mail postfix]# perl -MMIME::Base64 -e \

> 'print encode_base64("tester\@cngnu.org");'

dGVzdGVyQGNuZ251Lm9yZw==

[root@mail postfix]# perl -MMIME::Base64 -e \

> 'print encode_base64("testpw");'

dGVzdHB3

 

[root@mail postfix]# telnet localhost 25

Trying 127.0.0.1...
Connected to localhost.
Escape character is '^]'.
220 mail.cngnu.org ESMTP Postfix

EHLO cngnu

250-mail.cngnu.org

250-PIPELINING

250-SIZE 10240000

250-VRFY

250-ETRN

250-AUTH LOGIN PLAIN

250-AUTH=LOGIN PLAIN

250-XVERP

250 8BITMIME

AUTH LOGIN

334 VXNlcm5hbWU6

dGVzdGVyQGNuZ251Lm9yZw==

334 UGFzc3dvcmQ6

dGVzdHB3

235 Authentication successful

QUIT

221 Bye

Connection closed by foreign host.

  此时,由于还没有安装Cyrus-IMAP以及创建邮箱,所以还不能提交邮件,请继续下一步。

  这里使用Perl里面的MIME::Base64模块(需要安装,如perl -MCPAN -e 'install MIME::Base64')来取得这个验证串:perl -MMIME::Base64 -e 'print base64_encode("tester\0tester\0testpw");'来得到MIME-Base64编码的验证串。此外,你也可以使用mmencode来生成,mmencode可以在metamail这个包里面找到。

8.  安装Cyrus-IMAP

8.1.  下载

  http://asg.web.cmu.edu/cyrus/download/

[root@mail postfix]# cd /usr/src

[root@mail src]# wget ftp://ftp.andrew.cmu.edu/pub/cyrus-mail/cyrus-imapd-2.1.15.tar.gz

8.2.  编译与安装

  编译Cyrus-IMAP,并取消kerberos支持(在Redhat中,kerberos库有问题,很难编译通过,Mandrake则可以通过;此外,我们也不需要kerberos的支持;如果通不过,就指定kerberos的位置--with-krb=/usr/kerberos)和snmp的支持:

[root@mail src]# tar -zxf cyrus-imapd-2.1.15.tar.gz

[root@mail src]# cd cyrus-imapd-2.1.15

 

[root@mail cyrus-imapd-2.1.15]# ./configure --with-cyrus-prefix=/usr/cyrus \

> --with-sasl=/usr/local/lib/sasl2 --with-auth=unix \

> --without-ucdsnmp --with-krb=/usr/kerberos

 

[root@mail cyrus-imapd-2.1.15]# make depend

[root@mail cyrus-imapd-2.1.15]# make all CFLAGS=-O

[root@mail cyrus-imapd-2.1.15]# make install

  如果编译时提示没有找到com_err.h,请复制当前目录的et目录下面的com_err.h到/usr/include:

[root@mail cyrus-imapd-2.1.15]# cp et/com_err.h /usr/include

 

  Cyrus-IMAP的安装脚本有问题,cyradm(现在使用的是Perl版本,原来的TCL版本不再支持)所需要的perl模块被安装到一些不在Perl的@INC的目录里,需要手工安装。

 

[root@mail cyrus-imapd-2.1.15]# cd perl/imap

[root@mail imap]# perl Makefile.PL

[root@mail imap]# make install

 

8.3.  配置

  创建主配置文件/etc/cyrus.conf:

[root@mail imap]# cd ../..

[root@mail cyrus-imapd-2.1.15]# cp master/conf/small.conf /etc/cyrus.conf

  添加cyrus-imap的管理账号cyrus,并设置密码为“cyrus”(实际应用总可以使用更加复杂的密码),但是没有指定有效的SHELL,以防止使用它来登录:

[root@mail cyrus-imapd-2.1.15]# useradd -g mail -M -s/no/shell cyrus

[root@mail cyrus-imapd-2.1.15]# passwd cyrus

Changing password for user cyrus

New password: cyrus

BAD PASSWORD: it it too short

Retype new password: cyrus

passwd: all authentocation tokens updated successfully

 

  创建IMAP配置文件/etc/imapd.conf,管理员是cyrus:

[root@mail cyrus-imapd-2.1.15]# vi /etc/imapd.conf

 

configdirectory: /var/imap

partition-default: /var/spool/imap

admins: cyrus

sasl_pwcheck_method: saslauthd

sasl_mech_list: PLAIN

unixhierarchysep: yes

altnamespace: yes

  在/etc/imapd.conf中使用了unixhierarchysep: yes的配置可以创建带“.”的邮箱。关于imapd.conf可以参阅Cyrus-IMAP的文档来配置其他可用的参数。

 

  建立Cyrus-IMAP服务器的目录结构:

[root@mail cyrus-imapd-2.1.15]# mkdir -p /var/imap/sieve

[root@mail cyrus-imapd-2.1.15]# mkdir /var/spool/imap

 

[root@mail cyrus-imapd-2.1.15]# chown -R cyrus:mail /var/imap

[root@mail cyrus-imapd-2.1.15]# chown -R cyrus:mail /var/spool/imap

 

[root@mail cyrus-imapd-2.1.15]# su -s/bin/bash cyrus

bash-2.05$ tools/mkimap

bash-2.05$ exit

  这里tools/mkimap这个实用程序在cyrus-imap的源程序目录里面。

 

  创建日志:

[root@mail cyrus-imapd-2.1.15]# echo local6.debug /var/log/imapd.log >> /etc/syslog.conf

[root@mail cyrus-imapd-2.1.15]# echo auth.debug /var/log/auth.log >> /etc/syslog.conf

 

[root@mail cyrus-imapd-2.1.15]# /etc/rc.d/init.d/syslog restart

  设置邮件限额:

[root@mail cyrus-imapd-2.1.15]# chattr -R +S /var/imap/user

[root@mail cyrus-imapd-2.1.15]# chattr -R +S /var/imap/quota

[root@mail cyrus-imapd-2.1.15]# chattr -R +S /var/spool/imap

 

  由于Cyrus-IMAP的主控进程和Postfix的主控进程名字一样,容易混淆而且不方便控制,所以将Cyrus-IMAP服务器的主控进程做个别名连接:cyrusd。

[root@mail cyrus-imapd-2.1.15]# cd /usr/cyrus/bin

[root@mail bin]# ln -s master cyrusd

8.4.  运行

  启动命令如下:

[root@mail bin]# /usr/cyrus/bin/cyrusd&

8.5.  测试Cyrus-IMAP

  启动Cyrus-IMAP后,首先检查日志/var/log/messages、/var/log/imapd.log和/var/log/auth.log有无错误信息,然后检查进程,应该有如下进程存在:

[root@mail bin]# pstree |grep cyrusd

 

|-cyrusd

  接着检查端口,应该有如下端口打开:

[root@mail bin]# netstat -an |grep LISTEN

 

tcp  0  0 0.0.0.0:110  0.0.0.0:*  LISTEN

tcp  0  0 0.0.0.0:143  0.0.0.0:*  LISTEN

 

  现在创建邮箱。

  使用cyradm来创建和删除邮箱,它是Cyrus-IMAP自己带的交互式管理界面,现在的版本是用Perl写的。你也可以直接调用Cyrus::IMAP::Admin模块创建自己的CGI或脚本来做邮箱管理,可以参考Cyrus::IMAP::Shell模块的程序。

 

  为了支持虚拟域,我们采用了特定的用户邮箱名,用户的邮箱名与其邮件地址的全称很类似,只是将其中的“@”换成了“~”。这是由于,为了将虚拟域用户区别开来,我们希望使用用户的邮件全称来做它的邮箱名(其POP3/IMAP的登录名和邮箱名是一样的),但是虽然Cyrus-IMAP允许你创建带有“@”的邮箱,不过Postfix/smtpd却不支持邮件的本地部分含有@,它会在递交到Cyrus-IMAP的邮箱时,将“@”后面的部分作为域来处理,以至于不能正常递交。

  作为一个变通的方法,我们创建一个将用户邮件地址中的“@”换成“~”的邮箱,并使Postfix/smtpd通过FORWARD重写来递交到这里。首先在cyradm中创建两个信箱,分别是用“@”和“~”分隔的信箱名;然后在文件系统中删除分隔符为“@”的那个信箱目录,并给分隔符为“~”的信箱做个分隔符为“@”的符号链接。(之所以先在cyradm中创建分隔符为“@”的信箱然后在文件系统中删除,是为了让cyrus-imap知道有这样一个信箱。另外请注意,信箱名称中的点实际是用“^”代表的)

 

[root@mail bin]# cyradm --user cyrus localhost

IMAP Password:

mail.cngnu.org> cm user/cyrus

mail.cngnu.org> sq user/cyrus STORAGE 10240000

mail.cngnu.org> cm user/tester~cngnu.org

mail.cngnu.org> cm user/[email protected]

mail.cngnu.org> sq user/tester~cngnu.org STORAGE 10240000

mail.cngnu.org> lm

user/cyrus (HasNoChildren)    user/tester~cngnu.org (HasNoChildren)
user/[email protected] (HasNoChildren)

mail.cngnu.org> quit

[root@mail bin]# cd /var/spool/imap/user

[root@mail user]# ls

cyrus     tester~cngnu^org    tester@cngnu^org

[root@mail user]# rm -rf tester@cngnu^org

[root@mail user]# ln -s tester~cngnu^org tester@cngnu^org

[root@mail user]# cd -

  如果要删除一个IMAP邮箱,需要先给管理员cyrus授予C(Create)和D(Delete)的权限才可以删除。

[root@mail bin]# cyradm --user cyrus localhost

IMAP Password:

mail.cngnu.org> cm user/testdel

mail.cngnu.org> lm

user/cyrus (HasNoChildren)    user/tester~cngnu.org (HasNoChildren)
user/[email protected] (HasNoChildren)    user/testdel (HasNoChildren)

mail.cngnu.org> sam user/testdel cyrus cd

mail.cngnu.org> dm user/testdel

mail.cngnu.org> lm

user/cyrus (HasNoChildren)    user/tester~cngnu.org (HasNoChildren)
user/[email protected] (HasNoChildren)

mail.cngnu.org> quit

[root@mail bin]# rm -rf /var/spool/imap/user/testdel

 

  再检测POP3和IMAP服务:

[root@mail bin]# telnet localhost 110

+OK mail.cngnu.org Cyrus POP3 v2.1.15 server ready

USER [email protected]

+OK Name is a valid mailbox

PASS testpw

+OK Maildrop locked and ready

QUIT

+OK

[root@mail bin]# imtest -m login -a [email protected] localhost
C: C01 CAPABILITY
S: * OK mail.cngnu.org Cyrus IMAP4 v2.1.12 server ready
S: * CAPABILITY IMAP4 IMAP4rev1 ACL QUOTA LITERAL+ NAMESPACE UIDPLUS ID NO_ATOMIC_RENAME UNSELECT MULTIAPPEND SORT THREAD=ORDEREDSUBJECT THREAD=REFERENCES IDLE
S: C01 OK Completed
Password:
C: L01 LOGIN [email protected] {6}
+ go ahead
C: <omitted>
L01 OK User logged in
Authenticated.
Security strength factor: 0
. logout
* BYE LOGOUT received
. OK Completed

 

9.  安装IMP

9.1.  下载

  http://www.php.net/get_download.php?df=php-4.3.2.tar.gz

  http://www.horde.org/horde/

  http://www.horde.org/imp/3.2.1/

  http://www.horde.org/turba/

[root@mail bin]# cd /usr/src

[root@mail src]# wget http://www.php.net/distributions/php-4.3.2.tar.gz

[root@mail src]# wget ftp://ftp.horde.org/pub/horde/horde-2.2.1.tar.gz

[root@mail src]# wget ftp://ftp.horde.org/pub/pear/pear-1.0.1.tar.gz

[root@mail src]# wget ftp://ftp.horde.org/pub/imp/imp-3.2.1.tar.gz

[root@mail src]# wget ftp://ftp.horde.org/pub/turba/turba-1.2.tar.gz

 

9.2.  配置Apache与PHP

  IMP对PHP的环境要求较高。所以通常需要升级PHP包,并安装由Horde定制后的PEAR包。编译新的PHP包前请确认系统中存在Apache(这里使用了Apache 2)以及其它相关的软件包。

  RedHat的httpd-devel包中没有apache 2用来安装dso模块的脚本:instdso.sh,请自行从apache 2.x的发行包中取得,并放入/usr/lib/httpd/build中。

[root@mail src]# tar zxf php-4.3.2.tar.gz

[root@mail src]# cd php-4.3.2

[root@mail php-4.3.2]# ./configure --prefix=/usr --with-config-file-path=/etc \

> --with-mysql --with-apxs2 \

> --enable-ftp --enable-magic_quotes --with-xml \

> --with-gettext --with-imap \

> --with-imap-ssl --with-kerberos=/usr/kerberos

[root@mail php-4.3.2]# make

[root@mail php-4.3.2]# make install

[root@mail php-4.3.2]# [ -f /etc/php.ini ] && mv /etc/php.ini /etc/php.ini.orig

[root@mail php-4.3.2]# cp php.ini-dist /etc/php.ini

  修改/etc/php.ini,将register_globals功能打开。

register_globals = On

  安装PEAR包:

[root@mail php-4.3.2]# cd /usr/lib

[root@mail lib]# [-d php ] && mv php php.orig

[root@mail lib]# tar zxf /usr/src/pear-1.0.1.tar.gz

[root@mail lib]# mv pear php

  最后重新启动Apache:

[root@mail lib]# /etc/rc.d/init.d/httpd restart

9.3.  配置Horde

  安装Horde:

[root@mail lib]# cd /var/www/html

[root@mail html]# tar zxf /usr/src/horde-2.2.1.tar.gz

[root@mail html]# mv horde-2.2.1 horde

[root@mail html]# cd horde/scripts/db

 

[root@mail db]# mysql < mysql_create.sql

 

[root@mail db]# cd ../../config

[root@mail config]# for foo in *.dist; do cp $foo `basename $foo .dist`;done

  然后修改config目录下面的horde.php。

[root@mail config]# vi horde.php

  修改148行:

$conf['prefs']['driver'] = 'none';

  为:

$conf['prefs']['driver'] = 'sql';

  修改157行至162行,将其注释去掉并写入horde数据库的口令:

// $conf['prefs']['params']['phptype'] = 'mysql';
// $conf['prefs']['params']['hostspec'] = 'localhost';
// $conf['prefs']['params']['username'] = 'horde';
// $conf['prefs']['params']['password'] = '*****';
// $conf['prefs']['params']['database'] = 'horde';
// $conf['prefs']['params']['table'] = 'horde_prefs';

  为:

$conf['prefs']['params']['phptype'] = 'mysql';
$conf['prefs']['params']['hostspec'] = 'localhost';
$conf['prefs']['params']['username'] = 'horde';
$conf['prefs']['params']['password'] = 'horde';
$conf['prefs']['params']['database'] = 'horde';
$conf['prefs']['params']['table'] = 'horde_prefs';

  这里我们没有修改horde数据库的默认的数据库设置,如果在实际使用中,至少应该取一个比较复杂的密码。

 

  再来修改config目录下面的registry.php。

[root@mail config]# vi registry.php

  修改23行至24行,将其注释去掉:

// $this->registry['auth']['login'] = 'imp';
// $this->registry['auth']['logout'] = 'imp';

  为:

$this->registry['auth']['login'] = 'imp';
$this->registry['auth']['logout'] = 'imp';

  然后修改109、118行激活IMP和Turba:

'status' => 'inactive'

  为:

'status' => 'active'

  最后在浏览器中访问如下URL测试Horde需要的环境是否满足:

http://你的IMP服务器的IP/horde/test.php

  如果发现有红色的提示,可能需要修改你的PHP的安装和配置(参见上一节),然后再重新测试。

9.4.  配置IMP

  安装IMP:

[root@mail config]# cd ..

[root@mail horde]# tar zxf /usr/src/imp-3.2.1.tar.gz

[root@mail horde]# mv imp-3.2.1 imp

[root@mail horde]# cd imp/config

[root@mail config]# for foo in *.dist; do cp $foo `basename $foo .dist`;done

  然后修改config目录里面的conf.php:

[root@mail config]# vi conf.php

  修改37行:

$conf['menu']['apps'] = array();

  为:

$conf['menu']['apps'] = array('turba');

  修改57行:

$conf['user']['allow_resume_all'] = false;

  为:

$conf['user']['allow_resume_all'] = true;

  修改63行:

$conf['user']['allow_resume_all_in_drafts'] = false;

  为:

$conf['user']['allow_resume_all_in_drafts'] = true;

 

  然后修改prefs.php:

[root@mail config]# vi prefs.php

  将自动维护功能关闭,修改426、427行:

'value' => 1,
'locked' => false,

  为:

'value' => 0,
'locked' => true,

  再注释773行:

'value' => '',

  为:

//'value' => '',

  取消注释774行:

// 'value' => 'localsql',

  为:

'value' => 'localsql',

 

  最后修改servers.php:

[root@mail config]# vi servers.php

  注释除“cyrus”服务器外的所有服务器配置,然后修改“cyrus”服务器的配置为:

$servers['cyrus'] = array(
'name' => 'Cyrus IMAP Server',
'server' => 'localhost',
'protocol' => 'imap/notls',
'port' => 143,
'folders' => '',
'namespace' => 'INBOX.',
'maildomain' => 'cngnu.org',
'realm' => 'cngnu.org',
'preferred' => ''
);

 

9.5.  配置Turba

  安装Turba:

[root@mail config]# cd ../..

[root@mail horde]# tar zxf /usr/src/turba-1.2.tar.gz

[root@mail horde]# mv turba-1.2 turba

[root@mail horde]# cd turba/config

[root@mail config]# for foo in *.dist; do cp $foo `basename $foo .dist`;done

  然后修改config目录里面的conf.php:

[root@mail config]# vi conf.php

  修改32行:

$conf['menu']['apps'] = array();

  为:

$conf['menu']['apps'] = array('imp');

  然后修改config目录里面的sources.php:

[root@mail config]# vi sources.php

  修改140行:

'password' => '*****';

  为:

'password' => 'horde';

  最后,添加turba数据库表:

[root@mail config]# cd ../scripts/drivers

[root@mail config]# mysql -u horde -phorde <turba.sql

 

9.6.  测试IMP

  最后在浏览器中访问如下URL:

http://你的IMP服务器的IP/horde/

  输入用户名[email protected]和密码testpw登录。

10.  其他

10.1.  启动脚本

  可以编写一个启动脚本mailsys来启动这些进程,这样就不需要单独启动postfix和cyrusd了:

#!/bin/bash
#
# mailsys This shell script takes care of starting and stopping
# Postfix and Cyrus-IMAP.
# author : xingyu.wang <[email protected]> 2003/2/5
#
# chkconfig: 2345 80 30
# description: Postfix is a Mail Transport Agent, which is the program
# that moves mail from one machine to another.Cyrus-IMAP is a Mail # Deliver Agent, which provide POP3 and IMAP4 services for user and # deliver mail to local mailbox. # # processname: mailsys # pidfile: /var/run/mailsys.pid # Source function library. . /etc/rc.d/init.d/functions # Source networking configuration. . /etc/sysconfig/network # Check that networking is up. [ ${NETWORKING} = "no" ] && exit 0 [ -f /usr/sbin/postfix ] || exit 0 [ -f /usr/cyrus/bin/cyrusd ] || exit 0 RETVAL=0 prog="Mail System" start() { # Start daemons. echo -n $"Starting $prog: " echo -n $"SASL " /usr/local/sbin/saslauthd -a pam echo -n $"SMTP " /usr/sbin/postfix start > /dev/null 2>&1 & echo -n $"POP3 IMAP4 " /usr/cyrus/bin/cyrusd > /dev/null 2>&1 & RETVAL=$? if [ $RETVAL -eq 0 ]; then touch /var/lock/subsys/mailsys success $"$prog start" else failure $"$prog start failure" fi echo return $RETVAL } stop() { # Stop daemons. echo -n $"Shutting down $prog: " echo -n $"SMTP " /usr/sbin/postfix stop > /dev/null 2>&1 & echo -n $"POP3 IMAP4 " killproc cyrusd echo -n $"SASL " killproc saslauthd RETVAL=$? if [ $RETVAL -eq 0 ]; then rm -f /var/lock/subsys/mailsys success $"$prog stop" else failure $"$prog stop failure" fi echo return $RETVAL } # See how we were called. case "$1" in start) start ;; stop) stop ;; restart|reload) stop start RETVAL=$? ;; *) echo $"Usage: $0 {start|stop|restart}" exit 1 esac exit $RETVAL

 

[root@mail root]# chmod 755 /etc/rc.d/init.d/mailsys

[root@mail root]# cd /etc/rc3.d

[root@mail rc3.d]# ln -s ../init.d/mailsys S80mailsys

[root@mail rc3.d]# rm -rf S80sendmail

10.2.  整体测试

  创建邮箱后,测试发信功能:

[root@mail root]# mail [email protected]

Subject: test by me

this is a test.

.

CC:

[root@mail root]# mailq

Mail queue is empty

[root@mail root]# tail /var/log/mail/*

 

  使用mailq来查看邮件队列是否有错误,并查看/var/log/mail/*是否有错误信息。如果一切正常,说明信件已经发送到tester了。

  测试收信,先测试POP3:

[root@mail root]# telnet localhost 110

+OK mail.cngnu.org Cyrus POP3 v2.1.15 server ready

USER [email protected]

+OK Name is a valid mailbox

PASS testpw

+OK Maildrop locked and ready

LIST

1 400

TOP 1 10

Return-Path: <[email protected]>
X-Sieve: cmu-sieve 2.0
Return-Path: <[email protected]>
Received: by mail. (Postfix, from userid 0)
id 5F1EF90005; Mon, 20 May 2002 18:03:43 +0800 (CST)
To: [email protected]
Subject: test by me
Message-Id: <[email protected]>
Date: Mon, 20 May 2002 18:03:43 +0800 (CST)
From: [email protected] (root)

this is a test.

.

QUIT

+OK

  再测试IMAP:

[root@mail root]# imtest -m login -a [email protected] localhost
C: C01 CAPABILITY
S: * OK mail.cngnu.org Cyrus IMAP4 v2.1.15 server ready
S: * CAPABILITY IMAP4 IMAP4rev1 ACL QUOTA LITERAL+ NAMESPACE UIDPLUS ID NO_ATOMIC_RENAME UNSELECT MULTIAPPEND SORT THREAD=ORDEREDSUBJECT THREAD=REFERENCES IDLE
S: C01 OK Completed
Password:
C: L01 LOGIN tester {6}
+ go ahead
C: <omitted>
L01 OK User logged in
Authenticated.
Security strength factor: 0

. select inbox
* FLAGS (\Answered \Flagged \Draft \Deleted \Seen)
* OK [PERMANENTFLAGS (\Answered \Flagged \Draft \Deleted \Seen \*)]
* 1 EXISTS
* 1 RECENT
* OK [UIDVALIDITY 1021736432]
* OK [UIDNEXT 3]
. OK [READ-WRITE] Completed

. fetch 1:1 (FLAGS BODY[HEADER.FIELDS (DATE FROM)])
* 1 FETCH (FLAGS (\Seen) BODY[HEADER.FIELDS (DATE FROM)] {68}
Date: Mon, 20 May 2002 09:26:09 +0800 (CST)
From: [email protected]

)
. OK Completed
. logout
* BYE LOGOUT received
. OK Completed

 

  最后测试IMP,在浏览器中访问如下URL:

http://你的IMP服务器的IP/horde/

  输入用户名[email protected]和密码testpw登录。

 

  你也可以使用任何其它的邮件客户端程序来测试,如kmail、Outlook Express等等。

 

  OK,到此为止,我们的邮件系统就架设完毕了。如果有任何问题,请到http://www.anti-spam.org.cn/forums/的mail版讨论。