由于 PMail 后续更新,本文也将修改,适应最新版本


前言

最近想自建一个域名邮箱,开源的邮箱服务内存占用太高,对于个人使用不太友好,接着找到一个由 Golang 编写的域名邮箱Pmail。

官方介绍:PMail是一个追求极简部署流程、极致资源占用的个人域名邮箱服务器。单文件运行,包含完整的收发邮件服务和Web端邮件管理功能。只需一台服务器、一个域名、一行代码、一分钟部署时间,你就能够搭建出一个自己的域名邮箱。

GitHub地址:https://github.com/Jinnrry/PMail/

以下为界面截图:

20231028T200750_75320

准备工作

  • 服务器,开放了25号端口的服务器,没有开放则无法发信。
  • 域名
  • nginx 反代服务器
  • nginx proxy manager(可选,但建议),与nginx二选一
  • docker或者docker-compose

部署

提示:文章篇幅较长

docker-compose

如果服务器80,443端口没有被占用,搭建过程则较为简单。如果80,443端口被其他应用占用,搭建过程则较为繁琐。

本次80,443端口被nginx proxy manager占用,所以采用映射其他端口搭建

本次教程采用docker-compose方式安装,方便管理配置文件和升级。其余方式请参考官方教程

在你喜欢的目录下,新建 pamail 文件夹,在 pamil文件夹下,新建 docker-compose.yml文件,如:

mkdir -r ~/opt/pmail && cd ~/opt/pmail
docker network create pmail_network
vim docker-compose.yml

文件内容如下

version: '3.9'
services:
    pmail:
        container_name: pmail
        image: 'ghcr.io/jinnrry/pmail:latest'
        volumes:
            - './config:/work/config'
        ports:
            # pop
            - '110:110'
            - '995:995'
            # smtp
            - '25:25'
            - '465:465'
            # web访问
            - '8780:80'
            - '8781:443'
        restart: unless-stopped
        networks:
            - pmail_network

networks:
    pmail_network:
        external: true

配置文件编写完成之后,在 docker-compose.yml 所在目录下,运行

sudo docker compose up

接着会开启一个阻塞的前台进程,会打印日志信息,没有报错的话,服务则已经启动。

开放端口,因为使用的云服务器,所以需要在云服务器管理面板,开放安全组,也就是端口,笔者使用的阿里云。

进入 ecs管理面板,在左侧选择 【安全组】,选择服务器对应的安全组。

20231028T200750_57219

接着【手动添加】

20231028T200750_42854

填写端口范围和授权对象,端口即为配置文件开放的端口,授权对象为0.0.0.0,表示所有ip都可访问,描述为备注信息。

保存后,安全组配置完成。

配置pmail

暂停pamil的启动,修改配置文件

sudo vim /config/config.json

修改配置文件

"sslType":"1","httpPort":0,"httpsPort":0

网页访问服务器的公网ip+端口,如本次教程为 http://ip:8780,ip为服务器的公网ip,在ecs管理面板 可以看到。

欢迎界面,初次进入的页面如下:

20231028T200750_34250

下一步,选择数据库,建议默认即可,根据自己使用的数据库安装

image-20240727201528025

继续下一步,设置pmail管理员密码

image-20240727201551748

下一步,设置域名

image-20240727201611717

下一步,设置DNS,将以下信息添加到dns解析处,

image-20240727201646797

DNS记录配置,在上一步,需要将DNS记录添加到对应的域名,我使用的DNSPOD,点此跳转DNSPOD ,进入之后,按照提示添加记录即可

20231028T200750_47044

配置ssl,dns记录添加完成之后,回到pmail配置页面,继续配置证书。

image-20240727201730157

这里选择手动配置ssl证书,如果服务器的80端口没有被占用,可以选择自动配置,当然,前面的docker-compose.yml端口信息也需要改成80,443。

为什么选择不用80,443端口呢??

自动配置ssl需要用到80端口来验证服务器的所有权,所以自动配置ssl必须使用80端口。但是我的服务器安装了nginx proxy manger(简称npm) ,反代服务,一个web端的nginx工具,简化nginx配置,还可以一键生成ssl证书,我的服务器应用比较多,其他应用采用的都是子域名的方式访问。通过这种方式,简化的自己的工作、但是npm已经占用了80,443端口,所以80,443端口不可用。总不可能为了一个域名服务,让其他域名都不可用域名访问了吧。所以,将容器的80,443端口映射到了其他端口。

默认的证书位置在 ./config/ssl/private.key、./config/ssl/public.crt下,我们就把自己的ssl证书上传到 ./config/ssl下。

如果继续介绍npm申请ssl证书,这篇文章的篇幅就会过长。如果需要,到时候会另开文章介绍,这里就不多介绍了。也可自行搜索相关教程。

关于ssl配置可以参考这篇博文:Debian下的Certbot安装使用,附nginx使用

完成了这一步后,就基本完成了,不过还需要配置反向代理。

反向代理

dns记录

进入 dnspod管理页面,新增dns记录,如下

20231028T200750_68154

新增代理

进入npm管理页面,新增代理

20231028T200750_36487

点击 Add Proxy Host

20231028T200750_11375

编辑新增内容,按照如图所示编辑,打码的部分为服务的ip或者域名。

20231028T200750_57573

开启ssl,点击ssl,ssl证书选择已经申请的,如果没有,这里不做介绍。

强制ssl开启,http2开启,如图:

20231028T200750_18886

最后点击save保存。到这反向代理也配置完成。

但是访问会出现

20231028T200750_75626

修改pmail配置文件,关闭前台进程,ctrl+c,关闭。

pmail的配置文件已经挂载到本地了,在 config/config.json下,

进入pmail文件夹,编辑 config.json

cd ~/opt/pmail

sudo vim config/config.json 
  • httpsEnabled 配置改成2
  • sslType 改成1

启动测试

修改配置后,重新启动docker容器。

在 docker-compose.yml 所在目录下,运行

sudo docker up -d

# -d 表示后台运行

浏览器通过域名访问或者ip+端口访问即可

最终效果如下,

20231028T200750_25419

测试,发送测试邮件给163邮箱

20231028T200750_40126

163邮箱 接收

20231028T200750_15126

总结:

搭建过程较为繁琐,需要的前置条件较多.

pmail界面相较于其他邮箱要差一些,没有多用户功能,最新版已增加,实现了基本的收发功能。基本满足个人使用。

感谢作者的开源精神。

最后继续附上pmail的GitHub地址:https://github.com/Jinnrry/PMail/

附录

配置信息详解

{
"logLevel": "info", //日志输出级别
"domain": "domain.com", // 你的域名
"webDomain": "mail.domain.com", // web域名
"dkimPrivateKeyPath": "config/dkim/dkim.priv", // dkim 私钥地址
"sslType": "0", // ssl证书更新模式,0自动,1手动
"SSLPrivateKeyPath": "config/ssl/private.key", // ssl 证书地址
"SSLPublicKeyPath": "config/ssl/public.crt", // ssl 证书地址
"dbDSN": "./config/pmail.db", // 数据库连接DSN
"dbType": "sqlite", //数据库类型,支持sqlite 和 mysql
"httpsEnabled": 0, // web后台是否启用https 0默认(启用),1启用,2不启用
"spamFilterLevel": 0,// 垃圾邮件过滤级别,0不过滤、1 spf dkim 校验均失败时过滤,2 spf校验不通过时过滤
"httpPort": 80, // http 端口 . 默认 80
"httpsPort": 443, // https 端口 . 默认 443
"weChatPushAppId": "", // 微信推送appid
"weChatPushSecret": "", // 微信推送秘钥
"weChatPushTemplateId": "", // 微信推送模板id
"weChatPushUserId": "", // 微信推送用户id
"tgChatId": "", // telegram 推送chatid
"tgBotToken": "", // telegram 推送 token
"isInit": true // 为false的时候会进入安装引导流程
}