源码运行
电子邮件基于开源项目 Apache James Project 进行开发,James 是一个企业级的邮件服务器,支持 IMAP, SMTP, POP3 等多种协议。 James 支持使用 Mailet 和 Matcher 的概念来处理电子邮件。Mailet 是一个可以对邮件执行操作的处理程序,而 Matcher 则用于定义哪些邮件应该被特定的 Mailet 处理。 更多关于 James 的详细信息可以访问 James 官网
我们的电子邮件项目是 webmail,即网页端实现邮件的收发,对于 James 邮件服务器来说相当于中间层,对 James 进行调用实现邮件的收发,通过跟数字底座的结合实现了人员的同步,即数字底座的人员都会在 James 中有唯一的邮箱账号。
由于 James 是一个企业级的邮件服务器,所以在邮箱账号创建后我们也可使用独立的电子邮件客户端软件(如 Thunderbird、Foxmail 等)进行邮件的收发
James 安装运行
James 安装运行参考官方文档 https://james.apache.org/server/install.html
当前安装运行文档基于 James 版本 3.8.0
, 以域名 example.com
为例说明安装过程
软件需求
- Java 虚拟机。James-3.8.0 需要 Java 11 来运行
- 管理员用户权限。Linux/Unix 平台需要 root 用户权限, Windows 平台需要管理员用户权限
- Libc6。对于 Linux 平台还需要 Libc6 库来执行 james 的相应命令(以 Ubuntu 安装为例:
sudo apt-get install libc6-i386 libc6-dev-i386
) - 系统资源。系统需要足够的 CPU、内存、硬盘、网络带宽等系统资源,James 配置了使用 512 MB 内存,这些配置都需要根据自己的使用量来评估和调整
二进制包下载
对于没有服务器个性化需求的用户,可以直接从 James 下载页 下载二进制包进行部署,我们下载了 james-server-app-3.8.0-app.zip
。 其他的包则是在支持的特性上有所不同,具体可参考 James 的多种打包
生成密钥对
此步骤为后面某些协议启用 SSL/TLS 而做的准备,如不需要启用加密端口可跳过此步骤,但是更推荐启用并优先使用加密端口
$ keytool -genkey -alias james -keyalg RSA -storetype PKCS12 -keystore /Users/tobin/Documents/james/conf/keystore
输入密钥库口令:
再次输入新口令:
您的名字与姓氏是什么?
[Unknown]: test
您的组织单位名称是什么?
[Unknown]: test
您的组织名称是什么?
[Unknown]: test
您所在的城市或区域名称是什么?
[Unknown]: test
您所在的省/市/自治区名称是什么?
[Unknown]: test
该单位的双字母国家/地区代码是什么?
[Unknown]: test
CN=test, OU=test, O=test, L=test, ST=test, C=test是否正确?
[否]: y
命令执行完成后会生成密钥对并存储在密钥库文件 /Users/tobin/Documents/james/conf/keystore
中
配置文件修改
二进制包下载后解压,配置文件放在 conf
目录下
这里根据我们的需求修改相应的配置文件,由于某些配置文件内容较多,只列出需要修改的某块配置
以我们需要用 MySQL
来存储邮件和用户信息,并开启 SMTP
、IMAP
、POP3
协议为例,我们需要调整以下配置文件:
- domainlist.xml
<domainlist class="org.apache.james.domainlist.jpa.JPADomainList">
<autodetect>false</autodetect>
<autodetectIP>false</autodetectIP>
<defaultDomain>example.com</defaultDomain> <!-- 使用的邮箱域名,本地调试可保持 localhost 不调整 -->
</domainlist>
- mailetcontainer.xml
<mailetcontainer enableJmx="true">
<processors>
<processor state="transport" enableJmx="true">
<!-- 注释此 mailet,否则不能外发邮件 -->
<!-- <mailet match="RemoteAddrNotInNetwork=127.0.0.1" class="ToProcessor">
<processor>relay-denied</processor>
<notice>550 - Requested action not taken: relaying denied</notice>
</mailet> -->
</processor>
</processors>
</mailetcontainer>
- james-database.properties
调整使用 MySQL 作为邮件及用户信息的存储库,在 MySQL 中建 james
库
调整配置后需 将 MySQL 对应的驱动包放入 lib
文件夹 中,否则启动会报驱动找不到的错
database.driverClassName=com.mysql.cj.jdbc.Driver
database.url=jdbc:mysql://localhost:3306/james?serverTimezone=GMT%2B8&nullCatalogMeansCurrent=true&useUnicode=true&characterEncoding=utf-8&rewriteBatchedStatements=true&useCompression=true&useSSL=false&allowPublicKeyRetrieval=true
database.username=root
database.password=111111
vendorAdapter.database=MYSQL
- log4j2.xml
可以根据自己的需求调整日志存放的位置及相应代码的日志输出
- usersrepository.xml
<usersrepository name="LocalUsers" class="org.apache.james.user.jpa.JPAUsersRepository">
<algorithm>MD5</algorithm> <!-- 修改加密算法为 MD5,这里主要是用于数字底座的用户与 James 同步 -->
</usersrepository>
- smtpserver.xml
<smtpservers>
<smtpserver enabled="true">
<jmxName>smtpserver</jmxName>
<bind>0.0.0.0:25</bind>
<connectionBacklog>200</connectionBacklog>
<connectiontimeout>360</connectiontimeout>
<connectionLimit>0</connectionLimit>
<connectionLimitPerIP>0</connectionLimitPerIP>
<auth>
<announce>forUnauthorizedAddresses</announce> <!-- 对于未授权的地址开启认证 -->
<!-- <requireSSL>false</requireSSL> -->
<plainAuthEnabled>true</plainAuthEnabled> <!-- 启用明文认证,建议结合 SSL/TLS 使用 -->
</auth>
<authorizedAddresses>0.0.0.0</authorizedAddresses>
<maxmessagesize>0</maxmessagesize>
<addressBracketsEnforcement>true</addressBracketsEnforcement>
<handlerchain>
<handler class="org.apache.james.smtpserver.fastfail.ValidRcptHandler"/>
<handler class="org.apache.james.smtpserver.CoreCmdHandlerLoader"/>
</handlerchain>
</smtpserver>
<smtpserver enabled="true">
<jmxName>smtpserver-ssl</jmxName>
<bind>0.0.0.0:465</bind>
<connectionBacklog>200</connectionBacklog>
<tls socketTLS="true" startTLS="false"> <!-- 使用socketTLS,所有通信都是加密的 -->
<keystore>file://conf/keystore</keystore> <!-- keystore 位于 James 的 conf 目录中 -->
<keystoreType>PKCS12</keystoreType> <!-- 生成密钥对步骤中指定的密钥库的存储类型 -->
<secret>111111</secret> <!-- 生成密钥对步骤中指定的密钥库口令 -->
<provider>org.bouncycastle.jce.provider.BouncyCastleProvider</provider>
<algorithm>RSA</algorithm>
</tls>
<connectiontimeout>360</connectiontimeout>
<connectionLimit>0</connectionLimit>
<connectionLimitPerIP>0</connectionLimitPerIP>
<auth>
<announce>forUnauthorizedAddresses</announce> <!-- 对于未授权的地址开启认证 -->
<!-- <requireSSL>false</requireSSL> -->
<plainAuthEnabled>true</plainAuthEnabled>
</auth>
<authorizedAddresses>0.0.0.0</authorizedAddresses>
<maxmessagesize>0</maxmessagesize>
<addressBracketsEnforcement>true</addressBracketsEnforcement>
<handlerchain>
<handler class="org.apache.james.smtpserver.fastfail.ValidRcptHandler"/>
<handler class="org.apache.james.smtpserver.CoreCmdHandlerLoader"/>
</handlerchain>
</smtpserver>
</smtpservers>
- imapserver.xml
<imapservers>
<imapserver enabled="true">
<jmxName>imapserver</jmxName>
<bind>0.0.0.0:143</bind>
<connectionBacklog>200</connectionBacklog>
<connectionLimit>0</connectionLimit>
<connectionLimitPerIP>0</connectionLimitPerIP>
<plainAuthDisallowed>false</plainAuthDisallowed>
<auth>
<plainAuthEnabled>true</plainAuthEnabled> <!-- 启用明文认证,建议结合 SSL/TLS 使用 -->
</auth>
</imapserver>
<imapserver enabled="true"> <!-- 本地测试可根据自己需求移除这一块,减少配置 -->
<jmxName>imapserver-ssl</jmxName>
<bind>0.0.0.0:993</bind>
<connectionBacklog>200</connectionBacklog>
<tls socketTLS="true" startTLS="false"> <!-- 使用socketTLS,所有通信都是加密的 -->
<keystore>file://conf/keystore</keystore> <!-- keystore 位于 James 的 conf 目录中 -->
<keystoreType>PKCS12</keystoreType> <!-- 生成密钥对步骤中指定的密钥库的存储类型 -->
<secret>111111</secret> <!-- 生成密钥对步骤中指定的密钥库口令 -->
<provider>org.bouncycastle.jce.provider.BouncyCastleProvider</provider>
</tls>
<connectionLimit>0</connectionLimit>
<connectionLimitPerIP>0</connectionLimitPerIP>
<plainAuthDisallowed>false</plainAuthDisallowed>
<auth>
<plainAuthEnabled>true</plainAuthEnabled> <!-- 启用明文认证 -->
</auth>
</imapserver>
</imapservers>
- pop3server.xml
<pop3servers>
<pop3server enabled="true">
<jmxName>pop3server</jmxName>
<bind>0.0.0.0:110</bind>
<connectionBacklog>200</connectionBacklog>
<connectiontimeout>1200</connectiontimeout>
<connectionLimit>0</connectionLimit>
<connectionLimitPerIP>0</connectionLimitPerIP>
<handlerchain>
<handler class="org.apache.james.pop3server.core.CoreCmdHandlerLoader"/>
</handlerchain>
</pop3server>
<pop3server enabled="true">
<jmxName>pop3server-ssl</jmxName>
<bind>0.0.0.0:995</bind>
<connectionBacklog>200</connectionBacklog>
<tls socketTLS="true" startTLS="false">
<keystore>file://conf/keystore</keystore>
<keystoreType>PKCS12</keystoreType>
<secret>111111</secret>
<provider>org.bouncycastle.jce.provider.BouncyCastleProvider</provider>
</tls>
<connectiontimeout>1200</connectiontimeout>
<connectionLimit>0</connectionLimit>
<connectionLimitPerIP>0</connectionLimitPerIP>
<handlerchain>
<handler class="org.apache.james.pop3server.core.CoreCmdHandlerLoader"/>
</handlerchain>
</pop3server>
</pop3servers>
DNS 设置
对于互联网收发,需要设置相应的域名解析,如果域名设置处仍旧使用 localhost (仅用于本地的测试)则这步可跳过
记录类型 | 主机记录(域名前缀) | 记录值 |
---|---|---|
MX | @ | mail.example.com |
A | 邮件服务器公网 IP | |
A | pop | 邮件服务器公网 IP |
A | imap | 邮件服务器公网 IP |
A | smtp | 邮件服务器公网 IP |
运行
进入 bin
目录下执行命令 ./james start
即可启动 James
接下来就可以创建用户来收发邮件,可以通过命令 ./james-cli.sh adduser user@example.com 111111
创建用户, 其中 user@example.com
为用户邮箱(用户邮箱中的域名部分需跟配置文件 domainlist.xml
中设置的一致),111111
为对应的邮箱密码
服务器端口设置
一些服务器默认禁用了端口的互联网访问,所以需要对相应的端口放行才能正常的使用邮件服务
协议 | 非加密端口 | 加密端口 |
---|---|---|
SMTP | 25 | 465 |
POP3 | 110 | 995 |
IMAP | 143 | 993 |
至此,我们已经在 James 邮件服务器上新建了 user@example.com
邮箱,并且可以用这个邮箱在各个邮件服务器之间收发邮件了
webmail 安装运行
由于本项目依赖数字底座,数字底座在电子邮件中提供了单点登录认证、组织身份的服务,所以需要先将对应的数字底座服务启动,可参考数字底座源码运行文档
下载源码
前往 gitee 下载代码,地址: https://gitee.com/risesoft-y9/y9-email
后端项目
引入项目
打开 IDEA,点击左上角的 File
,在下拉选项中选择 Open
,找到源码目录选择最外层的根目录 y9-email 打开
修改配置文件
修改服务的配置文件 application.yml
,将 MySQL、Redis、Kafka 等服务端口和密码改为自己的服务地址和密码。
对于未使用的中间件,对应的设置可以不用修改,不同的数据库适配详细配置,请点击参考数据库适配,以下为 MySQL 数据库的数据源连接配置
risenet-y9boot-webapp-webmail
工程配置:
spring:
datasource:
druid:
y9-public:
driver-class-name: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://localhost:3306/y9_public?serverTimezone=GMT%2B8&nullCatalogMeansCurrent=true&useUnicode=true&characterEncoding=utf-8&rewriteBatchedStatements=true&useCompression=true&useSSL=false&allowPublicKeyRetrieval=true
username: root
password: 111111
webmail:
# 连接 james 的库,用于邮箱的管理
driver-class-name: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://localhost:3306/james?serverTimezone=GMT%2B8&nullCatalogMeansCurrent=true&useUnicode=true&characterEncoding=utf-8&rewriteBatchedStatements=true&useCompression=true&useSSL=false&allowPublicKeyRetrieval=true
username: root
password: 111111
y9:
app:
webmail:
# 需要修改为自己的邮件服务器域名
imapHost: imap.example.com
imapPort: 143
smtpHost: smtp.example.com
smtpPort: 25
host: example.com
运行
将服务的上下文修改为对应服务名,将 Tomcat 的端口调整为 7056
以便前端、或其他服务能正常调用
工程名字 | 服务名称 |
---|---|
risenet-y9boot-webapp-webmail | webmail |


添加完成之后选择相应的 Tomcat 点击 Debug
即可启动服务
前端项目
运行前提
node.js 版本 v14.20.0 或者更高版本
这个项目里的配置文件是对应这套开源代码的后端代码,需要先在本地环境中,将后端的代码运行起来,才能运行起来看到页面效果。
本地运行
打开 cmd
$ cd vue\y9vue-webmail # 进入前端工程文件夹
$ npm i # 安装依赖
$ npm run serve # 依赖安装完成后,运行程序
前端工程默认使用 7070 端口。
如果需要部署到其他环境,可以执行 npm run build 或者 npm run build-test 打包部署至正式或者测试环境,需要修改 .env.production 或者 .env.test 中的配置
访问服务
运行成功后,复制事项链接,打开浏览器访问:http://localhost:7070/webmail/
默认账号:
测试账号 登录名:user 密码:Risesoft@2022