基于数据库的虚拟域邮件系统的构建

12/3/2006来源:Qmail人气:7777

1、简介
本文对文献[1][2]的方案进行了扩充改进,组建了一个商业级的虚拟域邮件系统。主要增加了webmail和用户注册管理、磁盘限额等功能,改进了邮箱管理,解决了原sendmail用户平稳升级等问题。经实际检验,该方案实用,功能强大,可供构建或升级邮件系统借鉴。

操作系统:FreeBSD4.8 数据库MySQL3.23
SMTP代理:Postfix2 SMTP认证:Cyrus-Sasl2
Web邮件:OpenWebmail POP3:vm-pop3
认证模块:pam-mysql auth_mysql

2、用户表结构

字段名类别说明相关程序
userchar(20)lily用户账号pam owm pop3
namechar(30)test user用户全名owm
passwdchar(60) 密码pam owm pop
uidint(5)2000用户IDpostfix owm
gidint(5)2000组IDpostfix owm
homechar(60)/vhost/lily用户目录owm
addrchar(60)lily@test.com邮件地址postfix
mboxchar(20)lily邮箱名postfix owm
statusint(3)1状态可选
表1 用户表

3、安装和配置

3.1软件安装注意事项

这里没有给出完整的安装方法。本文所用软件均可用ports安装,安装过程很简单,只需在/usr/ports中找到相应软件,然后执行make install。详细的安装和测试方法见参考文献[1][2][3]。补充说明:
(1)安装FreeBSD时请选择安装cvsup,另外/var分区用于保存邮件队列,需要10G以上空间,并创建一个/vhost分区用作保存用户主目录。
(2)安装pam-mysql前需要安装gmake。pam-mysql安装时需要修改pam_mysql.c的源代码,删除第54行#define DEBUG。完装完后将/usr/local/lib/pam_mysql.so拷贝到/usr/local/lib/目录中。
(3)vm-pop3在安装后,需在/etc/inetd.conf添加一行:
pop3 stream tcp nowait root /usr/local/sbin/vm-pop3d vm-pop3d

3.2认证模块配置

3.2.1 创建数据库并添加数据
(1)创建数据库mail: create database mail;
(2)创建用户数据表mailuser:请根据表1用create table语句创建。
(3)添加用户以数据
INSERT INTO mailuser(user,name,uid,gid,passwd,home,mbox,addr) VALUES ('lily','test user',2000,2000,'*****','/vhost/lily', 'lily','lily@test.com');
注:密码是经过crypt函数加密,我是用vipw拷过来的,尚不知道如何从命令行生成,请网友帮忙解决一下。
(4)创建一个mysql系统用户mailsys,密码为batman,并限制只能本地访问。pam、postfix和openwebmail需要用mailsys用户访问数据库。
GRANT ALL ON mail.* TO mailsys@localhost IDENTIFIED BY 'batman';

3.2.2 配置pam
在pam配置文件(/etc/pam.conf)添加如下两行:
smtp auth required pam_mysql.so user=mailsys passwd=batman host=localhost db=mail table=mailuser usercolumn=user passwdcolumn=passwd crypt=1 sqllog=0
vm-pop3d auth required pam_mysql.so user=mailsys passwd=batman host=localhost db=mail table=mailuser usercolumn=user passwdcolumn=passwd crypt=1 sqllog=0
注:smtp和vm-pop3d使用pam_mysql.so模块进行认证。后面的参数为账号所在数据库、表等信息。crypt=1是使用des加密。sqllog=0是不在日志文件记录sql查询语句。
sqllog没有出现在在readme中,是从其网站中查到的。

3.2.3 配置postfix
(1)主配置文件/usr/local/etc/postfix/postfix.conf
virtual_transport = virtual #虚拟域设置
virtual_mailbox_base = /var/mail #用户邮箱目录
virtual_mailbox_domains = test.com #虚拟域名
virtual_uid_maps = static:2000 #用户ID
virtual_gid_maps = static:2000 #组ID
virtual_mailbox_maps=mysql:/usr/local/etc/postfix/mailbox.cf #用户邮箱映射文件
virtual_mailbox_limit = 10000000 #限制/var/mail中用户的邮箱大小为10M
broken_sasl_auth_clients = yes # SMTP认证
smtpd_sasl_auth_enable = yes #使用SMTP认证
smtpd_sasl_security_options = noanonymous #禁止匿名用户
mynetworks=192.168.0.0/24 , 127.0.0.0/8 #IP地址范围
smtpd_recipient_restrictions=permit_sasl_authenticated permit_mynetworks permit_auth_destination reject
注:为了减轻查询工作量,用户ID和组ID是静态的。可以模仿virtual_mailbox_maps将其改为动态的。考虑到一些邮件系统基于IP地址范围限制用户使用SMTP服务,为了平稳过渡,使用了mynetworks和permit_mynetworks参数。
(2)邮箱映射文件/usr/local/etc/postfix/mailbox.cf
hosts = localhost #数据库所在主机
user = mailsys #数据库系统用户名
passWord = batman #密码
dbname = mail #数据库名
table = mailuser #用户表
select_field =mbox #用户邮箱。见表1说明
where_field =addr #where查询字段

3.2.4 配置openwebmail
(1)mysql用户认证配置,/www/cgi-bin/openwebmail/auth_mysql.pl
my $SQLHost = "localhost"; #数据库所在主机
my $sqlusr = "mailsys"; #数据库系统用户名
my $sqlpwd = "batman"; #密码
my $auth_db = "mail"; #数据库名
my $auth_table = "mailuser"; #用户表
my $field_username = "user"; #用户名
my $field_password = "passwd"; #密码
my $field_realname = "name"; #用户全名
my $field_uid = "uid"; #用户ID
my $field_gid = "gid"; #组ID
my $field_home = "home"; #用户主目录
my $pass_type = "crypt"; #密码格式为DES加密
(2)openwebmail主配置文件,/www/cgi-bin/openwebmail/etc/openwebmail.conf
auth_module auth_mysql.pl #认证模块名
smtpauth yes #发信需要SMTP认证
mailspooldir /var/mail #用户邮箱所在目录
use_syshomedir yes #用户邮件保存在用户主目录
create_syshomedir yes #自动创建用户主目录(/vhost/xxx)
quota_module quota_du.pl #磁盘限额模块
quota_limit 30000 #用户主目录磁盘上限30M
spool_limit 10000 #收件箱上限10M /var/mail
注:openwebmail提供了两种磁盘模块quota_unixfs.pl和quota_du.pl。使用quota_unixfs.pl不支持虚拟用户。
(3)openwebmail的smtp认证配置文件,/www/cgi-bin/openwebmail/etc/smthauth.conf
smtpauth_username owm #用户名
smtpauth_password smtp_auth #密码
注:openwebmail系统的SMTP认证不够完善,它将配置文件中的用户名和密码提交给SMTP用户认证程序。还不能直接使用邮件用户自己的用户名和密码。可参考4.2.1节第3点的方法将用户owm添加到mailuser表中。

4、用php实现用户的注册和管理

我们这里只给出修改用户密码的PHP代码,其它功能模块的实现与下面程序类似,只需修改相应的mysql语句即可。

账号:

密码:


mysql_select_db("mail",$conn);
$mypass=crypt("$pass"); //密码用DES加密
$sql="update mailuser set passwd="'$mypass"' where user="'.$user"'";
$result=mysql_query($sql,$conn);
mysql_close_db("mail",$conn); ?>
注:代码分为两部分,上部分显示两个输入框分别输入用户名和密码,当用户点击确定按钮后,系统将输入框的内容交给chpass.php程序处理。下半部分是根据传入的变量$user和$pass,用sql语句修改mailuser数据库内$user的密码。


[1] Powerplane, Postfix + Cyrus-SASL + Cyrus-IMAPD + PgSQL HOWTO [J/OL]:
http://www.cnfug.org/journal/5/02.html , 2003-09-06.
[2] Postfix-Cyrus-Web-cyradm-HOWTO:
http://www.delouw.ch/linux/Postfix-Cyrus-Web-cyradm-HOWTO/html/index.html
[3] openwebmail readme:
http://turtle.ee.ncku.edu.tw/openwebmail/doc/readme.txt


,