# 自建邮件服务器&&mailserver

#### 端口检查

邮件系统需要使用到**25、587、465、143、993** 端口，请先检查端口是否被占用

- 25  SMTP 默认端口
- 587 SMTP 客户端发信端口
- 465 SMTP SSL 发信端口
- 143 IMAP 收信端口
- 993 IMAP SSL 收信端口

下图说明了需要的端口的关系

[![](https://iovhm.com/book/uploads/images/gallery/2025-02/scaled-1680-/263U2Gw33oIrlBal-image-1739292729219.png)](https://iovhm.com/book/uploads/images/gallery/2025-02/263U2Gw33oIrlBal-image-1739292729219.png)

**常见问题：25端口无法开启，多半是被系统内置的postfix服务占用了**
```
# 关闭系统内置服务
systemctl disable postfix
```



#### 使用docker-compose

```yaml

version: "3"
services:
  smtp-server:
    image: harbor.iovhm.com/hub/mailserver/docker-mailserver:latest
    container_name: mailserver
    hostname: mail.iovhm.com
    network_mode: host
    ports:
      - "25:25"   # STMP
      - "587:587" # STMP CLIENT
      - "465:465" # STMP SSL
      - "143:143" # IMAP
      - "993:993" # IMAP SSL
    volumes:
      - ./data/mail-data:/var/mail  
      - ./data/mail-state:/var/mail-state
      - ./data/mail-logs:/var/log/mail
      - ./data/mail-config:/tmp/docker-mailserver
      - /etc/localtime:/etc/localtime:ro
    environment:
      # 如果在不允许设置主机名的环境中运行，设置邮件服务器的主机名
      - OVERRIDE_HOSTNAME=mail.iovhm.com
      - SPOOF_PROTECTION=1

```

#### 需要在120秒内增加第一个用户，否则系统自动退出

```

# 进入到容器后执行
docker exec -it mailserver /bin/bash
# 增加第一个用户
setup email add admin@iovhm.com <password>

# 增加2个约定的管理邮箱（可以设置自动转发到外部邮箱,也可以设置转发到本域邮箱）
setup alias add postmaste@iovhm.com  your@163.com
# 没错，就是abuse,表示乱用举报邮箱
setup alias add abuse@iovhm.com  your@163.com

# 查看用户列表
setup email list
setup alias list

# 生成 DKIM 密钥
setup config dkim

```

#### 配置DNS记录

```

mail      IN  A      10.11.12.13
@         IN  MX  10 mail.example.com
@         IN  TXT    "v=spf1 mx ~all"
_dmarc    IN  TXT    "v=DMARC1; p=none; sp=none; adkim=r; aspf=r"


```

#### 增加DNS 

```

# 查看挂载目录生成的DKIM文本字符串
cat ./data/mail-config/opendkim/keys/iovhm.com

# 填入DNS，使之成为一行

mail._domainkey    IN  TXT  "v=DKIM1; h=sha256; k=rsa;p=XXXXXXXXXXXXXXX"

```
DNS配置检查网站：<https://www.helloinbox.email/>

#### 其他命令

```
# 进入到容器
docker exec -it mailserver /bin/bash

# 根据提示
setup help

# 修改密码

setup email update airdict@iovhm.com <new password>
```

#### 25出站端口被封，使用中继

**配置为中继后，则不能使用直接出站了**

##### 增加中继配置

```

# 增加中继说明，既所有来自*@iovhm.com的邮件使用smtp.163.com发送
setup relay add-domain iovhm.com smtp.163.com 465

# 增加中继账号
setup relay add-auth iovhm.com your@163.com <your password>

# 增加中继排除，既这个域使用默认中继
setup relay exclude-domain vpclub.cn

```

##### 需要增加3个配置文件

-  **./data/mail-config/postfix-main.cf**


```
# 开启SMTP TLS
smtp_use_tls=yes

# SASL 认证配置
relayhost = [smtp.163.com]:465
smtp_sasl_auth_enable = yes
smtp_sasl_password_maps = hash:/tmp/docker-mailserver/postfix-sasl-password.cf
sender_canonical_maps = regexp:/tmp/docker-mailserver/sender_canonical.cf
smtp_sasl_security_options = noanonymous
smtp_sasl_type=cyrus

# TLS 配置
smtp_tls_security_level = encrypt
smtp_tls_loglevel = 1
smtp_tls_wrappermode = yes
# smtp_tls_CApath = /etc/ssl/certs
# smtp_tls_CAfile = /etc/ssl/certs/ca-certificates.crt


```

- **./data/mail-config/postfix-relaymap.cf**

**此处可以使用(强烈建议)内置的命令行增加**

```

# 发向iovhm.com的邮件使用163中继
# 因为现在发邮件欺诈，几乎所有的中继邮箱都不允许修改发件人地址
# 收件方收到的邮件中发件人显示未中继邮箱
setup relay add-domain iovhm.com smtp.163.com 587

# 设置域使用默认中继发送
setup relay exclude-domain vpclub.cn

```

配置中继映射规则

```


@domain1.com        [smtp.mailgun.org]:587
@domain2.com        [smtp.sendgrid.net]:2525
@domain3.com


```

- 当发件人为 **@domain1.com** 时，使用 **smtp.mailgun.org:587** 中继发送
- 当发件人为 **@domain2.com** 时，使用 **smtp.sendgrid.net:2525** 中继发送
- 当发件人为 **@domain3.com** 时，不使用中继出站，但是会受默认RELAY_HOST影响

- **./data/mail-config/postfix-sasl-password.cf**

```
# 中继邮箱密码凭据
[smtp.163.com]:465 airdict@163.com:<your password>


```

使用postmap postfix-sasl-password.cf 生成db

- **./data/mail-config/postfix-sender-canonical.cf**

```

# 中继邮箱密码凭据规则

/.+/	your@163.com


```

使用postmap postfix-sender-canonical.cf 生成db