1.原理:邮件服务器和相应协议
2.安装一台邮件服务器:里面自然拥有两个服务器,用于邮件发送的SMTP服务器和用于邮件接收的POP3服务器。在计算机上是两个程序,分别对应25和110端口。
配置邮件服务器的网络范围(这里局域网),邮箱域名(可以有多个),然后创建两个实验账号。
3.使用Windows自带的telnet程序可以连接任何一台主机,访问其端口,这样可以遵循邮件发送和接收协议用一个账户向另一个账户发送邮件,另一个账户通过相应指令接收邮件。
发送:注意是连接本地主机和25端口
telnet localhost 25
ehlo regrge
auth login
YWFh----------------------->BASE64编码后的用户名、密码
MTIz
mail from:<aaa@xbai.com>
rcpt to:<ccc@xbai.com>
data
from:<aaa@xbai.com>
to:<bbb@xbai.com>
subject:test
空行!!!!
aaaaaaaaaaaaaaaaaaaaaaaaaaacccc
.
quit
注意发送的邮件头和内容之间一-定-要-有-一-个-空-行!!内容结束后一定要另起单独的一行输入一个点-号-表-示-结-束!!
接收:注意这一次连接的是110端口!!
telnet localhost 110--------------->注意是110端口!!和发送的端口不一样!!!是发送服务器!
user ccc
pass 123
stat
retr 2
quit
4.Outlook配置使用:
可以用Outlook配置管理,指定邮件发送和接收服务器的域名和需要管理的邮箱账号,那么可以用Outlook发送和接收邮件:
Outlook:发送和接收邮件的客户端软件。创建账号,填写存在的邮箱账号密码,填写发送和接收服务器,
那么可以连接,发送和接收邮件。---->我的配好后把服务器对应邮箱给清空了,全转到Outlook里面了!
并且通过telnet无法再访问!!必须新创建一个再试验了!!(创建ccc账户,成功接收!!)
但是明明是发往ccc也是从ccc收的,下面怎么显示to bbb???----->难道因为Outlook同一设置了bbb账
户???
+OK 易邮邮件服务器 5.2 POP3 Service Ready
user ccc
+OK welcome here
pass 123
+OK
stat
+OK 2 685
retr 2
+OK 233 octets
Return-Path: <aaa@xbai.com>
Received: from flx (unknown [127.0.0.1])
by xbai.com with CMailServer 5.2 SMTP; Tue, 21 Jun 2016 11:16:11 +0800
from:<aaa@xbai.com>
to:<bbb@xbai.com>
subject:test
aaaaaaaaaaaaaaaaaaaaaaaaaaacccc
.
quit
+OK bye
失去了跟主机的连接。
5.Socket编程与协议进行邮件服务
保持易邮服务器开启:
Java程序:本地主机localhost上aaa@xbai.com向本地主机localhost上的ccc@xbai.com发送邮件
package cn.itcast.socketmail;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.net.Socket;
public class SocketMail {
public static void main(String[] args){
BufferedReader br=null;
OutputStream out=null;
Socket socket=null;
try{
socket=new Socket("localhost",25);//连接一台主机邮件服务器端口(发送服务器,SMTP服务器)
//包装流,读(网络流)------->注意不是读命令行输入(System.in)!!
br=new BufferedReader(new InputStreamReader(socket.getInputStream()));
out=socket.getOutputStream();
System.out.println(br.readLine());//连接后先读取服务器发送的一行信息
//依据SMTP协议向服务器写一行,注意结尾加上换行符供服务器readLine识别此行,但这里的\r\n不够通用
//应该包装一下用包装流的newLine
out.write("ehlo fsdfs\r\n".getBytes());
//读两行回送消息
System.out.println(br.readLine());
System.out.println(br.readLine());
//继续按协议写,相当于操作系统命令行用telnet程序发送
out.write("auth login\r\n".getBytes());
//继续读一行回送,下面都以此类推...
System.out.println(br.readLine());
out.write("YWFh\r\n".getBytes());
System.out.println(br.readLine());
out.write("MTIz\r\n".getBytes());
System.out.println(br.readLine());
out.write("mail from:<aaa@xbai.com>\r\n".getBytes());
System.out.println(br.readLine());
out.write("rcpt to:<ccc@xbai.com>\r\n".getBytes());
System.out.println(br.readLine());
out.write("data\r\n".getBytes());
System.out.println(br.readLine());
//注意这里连续两个\r\n的地方是邮件头和内容间必-须-加-的-一-个-空-行!!
out.write("from:<aaa@xbai.com>\r\nto:<ccc@xbai.com>\r\nsubject:test\r\n\r\naaaaaaaaaaaccdsxf\r\n".getBytes());
//注意这里必须单-独-一-行-加-上-一-个-点-号表示内容结束!!
out.write(".\r\n".getBytes());
System.out.println(br.readLine());
out.write("quit\r\n".getBytes());
System.out.println(br.readLine());
}catch(Exception e){
throw new RuntimeException(e);
}finally{
if(br!=null){
try{
br.close();
}catch(Exception ex){
throw new RuntimeException(ex);
}
}
if(out!=null){
try{
out.close();
}catch(Exception ex){
throw new RuntimeException(ex);
}
}
if(socket!=null){
try{
socket.close();
}catch(Exception ex){
throw new RuntimeException(ex);
}
}
}
}
}
服务器那边ccc账号的邮箱成功收到一封邮件,客户端Java程序这边收到的结果:(由邮件服务器反馈发送)
220 ESMTP 易邮邮件服务器 5.2.2004.02.18 SMTP Service Ready
250-AUTH=LOGIN
250 AUTH LOGIN
334 VXNlcm5hbWU6
334 UGFzc3dvcmQ6
235 OK
250 OK
250 OK
354 send the mail data, end with .
250
221 SMTP SERVICE CLOSED
6.自己搭建邮件服务器:用SMTP协议转投邮件到其他网站邮箱时不需要用户名、密码的做法:去DNS服务器注册A记录,目标服务器根据你的来访ip和ehlo 后面填写的域名查找匹配A记录,如果匹配成功,则不需要用户名、密码。(必须如此,否则你架设一台服务器,让其他网站的邮箱给你发邮件,经过其他网站服务器转投,你不可能要求人家注册你的邮箱拥有在你网站的用户名密码)
Mx记录:转投邮件怎么找到目的主机?需要目标主机(注意上面的A记录是转投邮件的主机不需要用户名密码的情况)在DNS服务器上注册一条Mx记录,也是域名对应ip,那么通过别的邮件服务器向目标服务器转投时就会根据邮件发送者发送的目标邮箱的主机域名到DNS查找ip,向指定目标服务器转投: