Mail Server 邮件服务部署,实现自己的域名邮箱

AI 摘要: 本文介绍了邮件收发的基本逻辑和相关协议,以及搭建自己的域名邮箱的准备工作。重点讲解了使用Postfix进行邮件接收和发送,通过dovecot支持MUA的信件收取,以及阿里邮箱实现自己的域名邮箱。

1. 整体内容

  1. 了解基本的邮件收发逻辑,了解什么是MUA、MTA、MRA,MailBOX,以及收(IMAP/POP3)发(SMTP)邮件相关协议和端口,以及SSL的安全支持;
  2. 申请自己的独立域名,用做邮件域名
  3. 安装Postfix,进行邮件接收和发送
  4. 通过mail/mailx进行邮件的发送和接收本地验证
  5. 除非是在MTA上架设webmail,否则需要通过dovecot类似软件来支持MUA通过IMAP/POP3进行信件收取
  6. 大都数云厂商,都已经将SMTP功能给禁用(防止垃圾邮件),我们可以通过阿里邮箱来实现自己的域名邮箱(通过域名别名来实现)

2. 准备工作

2.1. 选择安装最新的Postfix包(可选)

CentOS下,默认安装了postfix包版本是2.10.1,可以通过Ghettoforge源:http://ghettoforge.org/index.php/Usage 进行更新,支持一些第三方的包的版本增强

1
2
3
4
5
6
7
// 安装Ghettoforge源
rpm -ivh http://mirror.ghettoforge.org/distributions/gf/gf-release-latest.gf.el7.noarch.rpm
wget http://mirror.ghettoforge.org/distributions/gf/RPM-GPG-KEY-gf.el7 -O /etc/pki/rpm-gpg/RPM-GPG-KEY-gf.el7

// 更新
yum erase postfix.x86_64
yum install postfix3 postfix3-ldap

2.2. 熟悉Mail命令

mailmailx,是Linux下默认的邮件管理工具,Mailx提供了用于交互式使用的增强功能,例如IMAP、也可用作邮件批处理语言,用于发送和接收邮件

常见命令:

  • ? : 帮助信息
  • help:帮助信息
  • list: 显示所有命令
  • h/headers: 打印活动邮件
  • d/delete: 删除邮件,比如delete 1-10,删除1-10的邮件
  • enter回车: 信件读取
  • mail xx@163.com: 发送邮件给xx

2.3. 熟悉mutt命令

mutt能够够透过pop3/imap之类的协议去读取外部的信件:mutt -f imaps://perf.plus,输入对应的用户名和密码,就可以查看到邮件清单了。

因为大多数大的邮件服务商,都会屏蔽掉不受信任的MUA来连入,上面的命令如果连入163邮箱就会报错!

2.4. 邮件域名与DNS

  1. 设置mx解析
  2. 解析完后,通过dig -t mx domain查看

3. 理论部分,Postfix邮件收发流程 1

3.1. 邮件发送:传输组件, MUA、MTA、MDA,以及SMTP协议

用户A发送邮件给用户B,邮件发送过程(以SMTP协议为例):

  1. A先注册邮件账号
  2. A的客户端邮件代理(MUA - Mail User Agent,类似Outlook和雷鸟这类客户端)连上A邮件传输代理(MTA - Mail Transfer Agent,类似寄件人),
  3. MTA功能:
    • 认证
    • 利用STMP(Simple Transfer Protocl)协议(prot 25),接收A的MUA发过来的邮件(含收件人、Subject、Content等),信件会先入到接收Queue
    • 决定邮件的去向:
      • 若是自己能处理的,则通过MDA( Mail Dilivery Agent)发送至用户的mailbox
      • 若是不是自己能处理的,则通过MDA(Mail Dilivery Agent)做转递(Relay)处理,转向下一部MTA服务器(也是用的SMTP协议)
  4. MDA功能:
    • 按MTA的要求做信件分发处理,比如传递给到B的MTA
    • 还支持过滤、自动回复等功能
  5. B用户连上B用户的MTA,完成取件操作

Tips:

  • 用户A需要取得MTA服务的权限,才能与之进行SMTP协议的邮件通信(即申请注册邮件账号、密码)
  • MUA不需要常驻,收件的时候MUA应用打开就可以
  • MailBox:即用户邮箱,存储在/var/spool/mail/使用者账号,若MTA所收到的信件是本机的使用者,MDA就会将信件送到该mailbox当中去啰

3.2. 接收:MRA,以及POP、IMAP协议

用户B的MUA从B的MRA (Mail Retrieval Agent)收邮件:

使用者可以透过 MRA 服务器提供的邮政服务协议 (Post Office Protocol, POP) 来收下自己的信件, 也可以透过 IMAP (Internet Message Access Protocol) 协议将自己的信件保留在邮件主机上面, 并进一步建立邮件数据匣等进阶工作。也就是说,当客户端收受信件时,使用的是MRA的POP3, IMAP等通讯协议,并非MTA的SMTP!

Tips:

  • Pop3(Post Office Protocl V3.0)协议,用的端口是port 110,默认情况收件后会删除MailBox中的邮件,除非客户端做操作要求MTA做备份;
  • IMAP(Internet Message )协议,用的端口是port 143,支持同一个用户在多个用户邮件代理下载查看邮件,默认收件后不会删除MailBox中的邮件,因此需要注意用Quta来限制用户磁盘空间!

3.3. 端口相关

  • 发送SMTP协议:
    • 默认SMTP端口25,开启TLS端口smtps port 465
  • 接收协议:
    • 默认POP端口110,开启TLS端口pop3s port 995
    • 默认IMAP端口143,开启TLS端口imaps port 993
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
$ cat /etc/services
// 默认
smtp            25/tcp          mail
smtp            25/udp          mail
pop3            110/tcp         pop-3           # POP version 3
pop3            110/udp         pop-3
imap            143/tcp         imap2           # Interim Mail Access Proto v2
imap            143/udp         imap2

// TLS默认端口
urd             465/tcp         smtps   # URL Rendesvous Directory for SSM / SMTP over SSL (TLS)
imaps           993/tcp                         # IMAP over SSL
imaps           993/udp                         # IMAP over SSL
pop3s           995/tcp                         # POP-3 over SSL
pop3s           995/udp                         # POP-3 over SSL

Tips:

若你使用了smtps,那么全世界与你的MTA沟通者, 通通需要改变为smtps通讯协议才行!这个工程实在太浩大了!

目前还没有任何一家 ISP 有能力进行! 所以,就造成目前没有 SMTPs 的协议啰。目前基本上是将邮件数据加密后,再交由MTA传送即可

3.4. Open Relay

你需要MTA帮你将信寄送到下一部MTA去时,这个动作就称为邮件转递 (Relay) 。若开启Relay,则短时间内就被很多人察觉,此时那些不法的广告信、色情垃圾信业者将会利用你的这部Open Relay MTA 发送他们的广告,你则因此可能:

  • 网络带宽占用
  • 收发占用服务器资源
  • MTA被其他MDA拉黑
  • 服务器IP被拉黑
  • 收发问题,导致客户流失
  • MTA被用于其他不法活动

4. MTA服务器Postfix部署安装

早期的sendmail用得很多,但存在安全、性能等问题,CentOS已经将预设的mail server调整为postfix(Venema博士在IMB一个年假期间开发出来的!)

4.1. Postfix核心配置

注意配置在/etc/postfix/

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
// postfixMTA主配置
/etc/postfix/main.cf

// postfix每个程序运作参数
/etc/postfix/master.cf

// 设定开放 Relay 或拒绝联机的来源或目标地址等信息,需要在main.cf卡开启,设定完后通过postmap处理
/etc/postfix/access (利用 postmap 处理)

// 邮件分组、邮件别名操作
/etc/aliases (利用 postalias 或 newaliases 均可)

4.2. Postfix核心命令

可以通过man postfix的See Also部分查看更多关于Postfix指令

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
// 查看配置,postconf -n
/usr/sbin/postconf

// Daemon启停
/usr/sbin/postfix
    - postfix check 配置、权限检测
    - postfix start|stop|status
    - postfix flush 冲刷MTA邮件MQ队列,寄件
    - postfix reload 重载main.cf配置

// ASCII别名配置转存入到/etc/aliases.db中
/usr/sbin/postalias
    - postalias hash:/etc/aliases

// 查看MTA队列中的邮件内容
/usr/sbin/postcat

// 转换/etc/postfix/access配置到数据库
/usr/sbin/postmap
    - postmap hash:/etc/postfix/access

// 邮件队列管理
/usr/sbin/postqueue
    - postqueue -p

4.3. MTA的信件分析流程

标头分析通过后,你的信件内容才会开始上传到主机的队列,然后透过 MDA 来处理该信件的流向:

4.4. postfix main.cf的核心配置情况

通过postconf -n 查看到我们的配置情况,细节解释可以参考:2

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
// postconf -n
alias_database = hash:/etc/aliases
alias_maps = hash:/etc/aliases
broken_sasl_auth_clients = yes
command_directory = /usr/sbin
config_directory = /etc/postfix
daemon_directory = /usr/libexec/postfix
data_directory = /var/lib/postfix
debug_peer_level = 2
debugger_command = PATH=/bin:/usr/bin:/usr/local/bin:/usr/X11R6/bin $daemon_directory/$process_name $process_id & sleep 5
html_directory = no

// 网络接口支持
inet_interfaces = all
inet_protocols = all

mail_owner = postfix
mailq_path = /usr/bin/mailq.postfix
manpage_directory = /usr/share/man

// MTA邮件接收设置
mydestination = $myhostname, localhost
mydomain = $myhostname
myhostname = perf.plus

// MTA网络设定
mynetworks = 127.0.0.0/8, 192.168.100.0/24, hash:/etc/postfix/access
myorigin = $myhostname

newaliases_path = /usr/bin/newaliases.postfix
queue_directory = /var/spool/postfix
readme_directory = /usr/share/doc/postfix-2.10.1/README_FILES
recipient_delimiter = +

// MRA相关设定
relay_domains = $mydestination
sample_directory = /usr/share/doc/postfix-2.10.1/samples
sendmail_path = /usr/sbin/sendmail.postfix
setgid_group = postdrop

// smtpd接收者设定&sasl支持
smtpd_recipient_restrictions = permit_mynetworks, permit_sasl_authenticated, reject_unknown_sender_domain, reject_unknown_recipient_domain, reject_unauth_destination, reject_rbl_client cbl.abuseat.org, reject_rbl_client bl.spamcop.net, reject_rbl_client cblless.anti-spam.org.cn, reject_rbl_client sbl-xbl.spamhaus.org, check_policy_service unix:/var/spool/postfix/postgrey/socket
smtpd_sasl_auth_enable = yes
smtpd_sasl_security_options = noanonymous
unknown_local_recipient_reject_code = 550

5. 利用dovecot设定MRA,支持pop3以及imap

5.1. dovecot安装和配置

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
// 1. 安装
yum install dovecot

// 2. 核心配置支持imap和pop3
vim /etc/dovecot/dovecot.conf
...
protocols = imap pop3

// 3. 生成ssl证书并移到/etc/dovecot目录,让imap/pop升级到ssl加密传输
cd /etc/pki/tls/certs/
make mydomain-mail.pem
mv mydomain-mail.pem /etc/dovecot && restorecon -Rv /etc/dovecot

// 4. 认证ssl配置,非加密port 110/143(pop3/imap),加密port 993/995(imaps/pop3s)
vim /etc/dovecot/conf.d/10-ssl.conf
ssl = required
ssl_cert = </etc/pki/dovecot/vbirddovecot.pem
ssl_key =  </etc/pki/dovecot/vbirddovecot.pem

// 5. 禁用明文认证
vim /etc/dovecot/conf.d/10-auth.conf
disable_plaintext_auth = yes 

// 6. 禁用非加密的服务
vim /etc/dovecot/conf.d/10-master.conf
inet_listener imap {
    port = 0     <== 15 行改成这样
  }
  inet_listener pop3 {
    port = 0     <== 36 行改成这样
  }

// 7. 指定邮件位置(很重要)
vim /etc/dovecot/conf.d/10-mail.conf
mail_location = mbox:~/mail:INBOX=/var/mail/%

// 8. 重启dovecot服务,查看端口情况
Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address           Foreign Address         State       PID/Program name
tcp        0      0 0.0.0.0:465             0.0.0.0:*               LISTEN      29203/master
tcp        0      0 0.0.0.0:25              0.0.0.0:*               LISTEN      29203/master
tcp        0      0 0.0.0.0:993             0.0.0.0:*               LISTEN      29324/dovecot
tcp        0      0 0.0.0.0:995             0.0.0.0:*               LISTEN      29324/dovecot

5.2. postfix支持smtps

1
2
3
// 编辑postfix配置,取消注释
vim /etc/postfix/master.cf
smtps     inet  n       -       n       -       -       smtpd

6. 基于Cyrus SASL 开放SMTP身份验证

通常,我们不能只能将邮件发送服务公共开放出来,因为这样会导致大量垃圾邮件的泛滥。

MTA可以通过在main.cf配置中设定mynetworks来指定受信任的网络,但若MUA的网络是变动的,则可以利用开放SMTP认证通过后,进行邮件Relay处理;

所以,当你的MUA通过SMTP协议进行邮件发送之前,需要做身份验证,这块通过Cyrus SASL软件实现:

6.1. 安装Cyrus SASL

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
// 安装和启动saslauthd服务
yum install cyrus-sasl cyrus-sasl-plain cyrus-sasl-md5
saslauthd -v

// 选定pam机制认证
vim /etc/sysconfig/saslauthd
MECH=pam

// sasl支持smtpd
vim /etc/sasl2/smtpd.conf
..
log_level: 3                <==登录文件信息等级的设定,设定 3 即可
pwcheck_method: saslauthd   <==就是选择什么服务来负责密码的比对啊
mech_list: plain login      <==那么支持的机制有哪些之意!


// 配置postfix,开启saslauthd认证
vim /etc/postfix/main.cf
..
// 1. 在本档案最后面增加这些与 SASL 有关的设定资料:
smtpd_sasl_auth_enable = yes
smtpd_sasl_security_options = noanonymous
broken_sasl_auth_clients = yes
// 2. 然后找到跟 relay 有关的设定项目,增加一段允许 SMTP 认证的字样:
smtpd_recipient_restrictions =
     permit_mynetworks,
     permit_sasl_authenticated,  <==重点在这里!注意顺序!
     reject_unknown_sender_domain,
     reject_unknown_recipient_domain,
     reject_unauth_destination,
     reject_rbl_client cbl.abuseat.org,
     reject_rbl_client bl.spamcop.net,
     reject_rbl_client cblless.anti-spam.org.cn,
     reject_rbl_client sbl-xbl.spamhaus.org,
     check_policy_service unix:/var/spool/postfix/postgrey/socket

// 校验
telnet localhost 25
...
ehlo localhost
250-AUTH LOGIN PLAIN    <==你得要看到这两行才行呦!
250-AUTH=LOGIN PLAIN
...
quit

到此,应该可以实现了SMTP的邮件认证功能。

7. 遇到的一些问题

7.1. Postfix - IMAP的认证失败,权限问题

1
imap(user): Error: chown(/home/user/mail/.imap/INBOX, group=12(mail)) failed: Operation not permitted (egid=1000(user), group based on /var/mail/user - see http://wiki2.dovecot.org/Errors/ChgrpNoPerm)

解决方案:chmod 0600 /var/mail/*

参见:https://wiki2.dovecot.org/Errors/ChgrpNoPerm

7.2. Postfix - SMTP无法进行邮件发送

阿里云服务器无法支持smtp发送邮件问题的原因是因为,阿里云屏蔽了smtp功能(防止垃圾邮件等问题),我们可以通过阿里邮箱:https://qiye.aliyun.com/ 进行邮件收发。

7.3. SMTP开启了smtps465端口,认证失败

可以通过25端口不加密的smtp+密码连入,但通过465端口加密+密码就无法连入,从/var/log/maillog看到的情况就是阻塞:

1
2
3
4
5
// 无法
Feb 23 00:50:50 tkstorm_proxy postfix/smtpd[30199]: connect from unknown[59.63.206.215]
...
Feb 23 00:51:20 tkstorm_proxy postfix/smtpd[30199]: lost connection after UNKNOWN from unknown[59.63.206.215]
Feb 23 00:51:20 tkstorm_proxy postfix/smtpd[30199]: disconnect from unknown[59.63.206.215]

以下这篇文章有简述了,SMTP以及SMTPS,以及25、465、587几个端口的由来和后续发展:

https://www.linuxbabe.com/mail-server/enable-smtps-port-465-postfix

8. 基于域名+阿里邮箱实现拥有自己域名的邮箱

我们可以通过企业邮箱方式进行邮件发送,可以支持阿里邮箱免费版(支持更换域名即a.com换到b.com可以,不要过于频繁就ok,我因为来回切了几次,锁定一周后再试),免费邮箱有邮箱账号限制(50个),支持邮件组(1000个),总容量有250G,默认账号是5G,如果是个人用,应该足够了。

阿里邮箱默认开头了一个postmaster@domain.com的管理Master账号,可以通过主账号管理子账号,用户可以通过子账号+密码,在MUA配置IMAPs/POP3s以及SMTPs相关,进行邮件的收发工作;

添加的子账号首次登陆会要求更改登陆密码,同时可以用于后续MUA的收发认证使用。

8.1. 主域名解析

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
解析的域名 记录类型  优先级 解析记录值
@       MX          5   mx1.qiye.aliyun.com
@       MX          10  mx2.qiye.aliyun.com
@       MX          15  mx3.qiye.aliyun.com
POP3    CNAME   -   pop.qiye.aliyun.com
IMAP    CNAME   -   imap.qiye.aliyun.com
SMTP    CNAME   -   smtp.qiye.aliyun.com
@       TXT     -   v=spf1 include:spf.qiye.aliyun.com -all

// 或者用
操作解析的域名 解析记录类型  优先级 解析记录值
@   MX  5   mxn.mxhichina.com.
@   MX  10  mxw.mxhichina.com.
pop3    CNAME    -  pop3.mxhichina.com.
imap    CNAME    -  imap.mxhichina.com
smtp    CNAME    -  smtp.mxhichina.com.
mail    CNAME    -  mail.mxhichina.com.
@       TXT      -  v=spf1 include:spf.mxhichina.com -all

8.2. 域别名功能

阿里邮箱,支持域名别名功能。

支持将1个域别名映射到同一个主域名上一同使用,主域名下所有用户都可以用别名域进行收发信。

比如主域名是x.com,给它绑定域别名y.com,那么登录a@x.com和a@y.com其实是访问同一个邮箱,发往a@y.com的邮件也就是发给a@x.com。

8.3. 别名域名解析设置

如果除了主域名外,还想利用域名别名来做到同样的邮件收发,可以通过在阿里邮箱Master账号中,设置域名别名,并做好相应的域名解析。

参考:3

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
// 域名配置相关
@   MX  默认  mxw.mxhichina.com | 10
@   MX  默认  mxn.mxhichina.com | 5
alimailchnymt   CNAME   默认  mail.mxhichina.com

// 配置完后,通过dig检测下
$dig -t mx lupguo.cool
...
lupguo.cool.        600 IN  MX  10 mxw.mxhichina.com.
lupguo.cool.        600 IN  MX  5 mxn.mxhichina.com.

小结

基于Postfix进行邮件收发,对邮件服务的整体流程有了简单的了解,与MAIL服务相关的概念有MUA\MTA\MRA;

相关的协议有接收IMAP(143)POP3(110),以及简单传输邮件协议:SMTP(25),对应的传输方面可以加上SSL支持:IMAPs(993)和POP3s(995),以及对应的加密传输服务有SMTPs(465)

除非是直接在MTA上面部署Webmail,否则邮件用户通过需要通过MUA基于IMAP/POP3协议从MTA上面接收邮件,需要通过dovecot软件支持;

在认证方面,需要通过Cyrus SASL软件来支持;

针对调试方面,可以基于/var/log/maillog进行对应的日志调试,分析遇到的问题;

邮件发送方面,可以基于mail/mailx进行简单的邮件收发,另外可以通过mutt命令基于imap/pop协议与MTA进行通信,完成邮件收信处理;

在云服务器方面,因为大部分ISP服务商,包括阿里云都禁止了STMP的邮件发送功能,可以通过第三方的云服务+域名别名实现自己的个性邮件名;

如果有什么问题,可以通过 lupguo@lupguo.cool 进行交流。