java 邮件组件_java组件开发(21)邮件发送组件mysmtp

邮件发送组件:mysmtp

在发送电子邮件时,可以通过使用引入JavaMail来达到这个目的,但是JavaMail本身在使用上还是比较复杂,特别是处理TLS、SSL加密以及附件的发送上比较麻烦。故本节通过对其封装,达到简便使用的效果,在日后编程中可以直接使用。

JavaMail不是标准的JDK的一部分,所以需要引入mail.jar到claasPath。另外还使用了commons.logging和log4j.jar作为日志输出,同时还使用了前面我们开发的commons.jar。

组件名: mysmtp

版本: 1.1

依赖包:commons-logging-1.1.1.jar、log4j-1.2.15.jar、mail.jar、commons_2010_10_17.jar

作者:UnclePeng

对象建模:

1、SMTPSetting,发送邮件需要用户名,密码,端口,加密算法,smtp地址等设置,所以集合这些属性,形成SMTP的设置类: SMTPSetting

2、MailMessage,邮件除了正文外,还有标题,收件人,回复人,抄送人,密送人等等属性,集合这些属性,形成邮件消息类: MailMessage

3、Attachment,除了文字外,邮件有时还带有附件,供MailMessage引用,Attachment直接引用本地或者网络路径上的文件路径。

4、MailSender,外部调用入口,该类初台化三个不同的seesion,分别是正常的session、ssl session、tls session,根据不同配置选择不同的session来发送邮件。

源码:

1、SMTPSetting.java

/*

*@# SMTPSetting.java 2:55:44 PM Jul 17, 2009

*Copyright 2009 UnclePeng, Inc. All rights reserved.

*/

package com.upeng.mysmtp;

/**

*

SMTP设置

* @author Lucky

* 2:55:44 PM Jul 17, 2009

*/

public class SMTPSetting {

/**加密协议**/

public enum SMTPEncrypt{

NORMAL, SSL ,TLS;

}

//用户名

private String userName = "";

//密码

private String pwd = "";

//SMTP地址

private String smtpHost;

//端口

private int port = 25;

//加密协议

private SMTPEncrypt enc = SMTPEncrypt.NORMAL;

/**

* @param userName用户名

* @param pwd密码

* @param smtpHostSMTP地址

* @param port端口

* @param enc加密协议

*/

public SMTPSetting(String userName , String pwd , String smtpHost , int port , SMTPEncrypt enc){

this.userName = userName;

this.pwd = pwd;

this.smtpHost = smtpHost;

this.port = port;

this.enc = enc;

}

/**

* @param userName用户名

* @param pwd密码

* @param smtpHostSMTP地址

* @param port端口

*/

public SMTPSetting(String userName , String pwd , String smtpHost , int port){

this.userName = userName;

this.pwd = pwd;

this.smtpHost = smtpHost;

this.port = port;

}

/**

* @param userName用户名

* @param pwd密码

* @param smtpHostSMTP地址

* @param enc加密协议

*/

public SMTPSetting(String userName , String pwd , String smtpHost , SMTPEncrypt enc){

this.userName = userName;

this.pwd = pwd;

this.smtpHost = smtpHost;

this.enc = enc;

}

/**

* @param userName用户名

* @param pwd密码

* @param smtpHostSMTP地址

*/

public SMTPSetting(String userName , String pwd , String smtpHost){

this.userName = userName;

this.pwd = pwd;

this.smtpHost = smtpHost;

}

public SMTPSetting(){

}

/**

* @return the userName

*/

public String getUserName() {

return userName;

}

/**

* @param userName the userName to set

*/

public void setUserName(String userName) {

this.userName = userName;

}

/**

* @return the pwd

*/

public String getPwd() {

return pwd;

}

/**

* @param pwd the pwd to set

*/

public void setPwd(String pwd) {

this.pwd = pwd;

}

/**

* @return the smtpHost

*/

public String getSmtpHost() {

return smtpHost;

}

/**

* @param smtpHost the smtpHost to set

*/

public void setSmtpHost(String smtpHost) {

this.smtpHost = smtpHost;

}

/**

* @return the port

*/

public int getPort() {

return port;

}

/**

* @param port the port to set

*/

public void setPort(int port) {

this.port = port;

}

/**

* @return the enc

*/

public SMTPEncrypt getEnc() {

return enc;

}

/**

* @param enc the enc to set

*/

public void setEnc(SMTPEncrypt enc) {

this.enc = enc;

}

}

说明:

SMTPSetting里面定义了三个不同加密类型的枚举,分别是不加密、SSL加密和TLS加密,默认是不加密

SMTP默认发送端口是25,可以更改,用户名和密码在需要的时候根据实际情况设置。

2、Attachment.java

/*

*@# Attachment.java 11:06:54 AM Jun 24, 2009

*Copyright 2009 UnclePeng, Inc. All rights reserved.

*/

package com.upeng.mysmtp;

import com.upeng.commons.io.FileUtils;

/**

*

附件

* @author Lucky

* 11:06:54 AM Jun 24, 2009

*/

public class Attachment {

//文件名

private String fileName;

//文件大小

private int fileSize;

//文件路径

private String filePath;

/**

*

获取文件名

* @return

*/

public String getFileName() {

if(this.fileName == null){

this.fileName = FileUtils.getFileName(filePath);

}

return fileName;

}

/**

*

设置文件名

* @param fileName文件名

*/

public void setFileName(String fileName) {

this.fileName = fileName;

}

/**

*

获取文件大小

* @return

*/

public int getFileSize() {

return fileSize;

}

/**

*

设置文件大小

* @param fileSize 文件大小

*/

public void setFileSize(int fileSize) {

this.fileSize = fileSize;

}

/**

* @return the filePath

*/

public String getFilePath() {

return filePath;

}

/**

* @param filePath the filePath to set

*/

public void setFilePath(String filePath) {

this.filePath = filePath;

}

}

3、MailMessage

/*

*@# MailMessage.java 11:28:41 AM Jun 24, 2009

*Copyright 2009 UnclePeng, Inc. All rights reserved.

*/

package com.upeng.mysmtp;

import java.util.ArrayList;

import java.util.Date;

import java.util.List;

import javax.activation.DataHandler;

import javax.activation.DataSource;

import javax.activation.FileDataSource;

import javax.mail.Address;

import javax.mail.Message;

import javax.mail.MessagingException;

import javax.mail.Message.RecipientType;

import javax.mail.internet.InternetAddress;

import javax.mail.internet.MimeBodyPart;

import javax.mail.internet.MimeMessage;

import javax.mail.internet.MimeMultipart;

import javax.mail.internet.MimeUtility;

import org.apache.commons.logging.Log;

import org.apache.commons.logging.LogFactory;

import com.upeng.commons.lang.StringUtils;

/**

*

邮件消息

* @author Lucky

* 11:28:41 AM Jun 24, 2009

*/

public class MailMessage {

private static final Log logger = LogFactory.getLog(MailMessage.class);

//分隔符

private static final String SEPARATOR = ":";

//常见错误分隔符

private static final String USUALLY_ERROR_SEPARATOR = ":";

//发件人Email地址

private String from;

//收件人列表

private List to = new ArrayList();

//抄送人列表

private List cc = new ArrayList();

//密送人列表

private List bcc = new ArrayList();

//日期

private Date date;

//邮件标题

private String subject;

//邮件正文

private String body;

//附件列表

private List attachments = new ArrayList();

//邮件大小

private int size;

//邮件优先级,默认为3

private int priority = 3;

private List replyList = new ArrayList();

/**

*

获取发件人信息

* @return the 发件人信息

*/

public String getForm() {

return from;

}

/**

*

设置发件人信息

* @param form 发件人信息

*/

public void setForm(String from) {

this.from = from;

}

/**

*

获取收件人列表

* @return 收件人列表

*/

public List getTo() {

return to;

}

/**

*

设置收件人列表

* @param to 收件人列表

*/

public void setTo(List to) {

this.to = to;

}

/**

*

获取抄送人列表

* @return 抄送人列表

*/

public List getCc() {

return cc;

}

/**

*

设置抄送人列表

* @param cc 抄送人列表

*/

public void setCc(List cc) {

this.cc = cc;

}

/**

*

获取密送人列表

* @return 密送人列表

*/

public List getBcc() {

return bcc;

}

/**

*

设置密送人列表

* @param bcc 密送人列表

*/

public void setBcc(List bcc) {

this.bcc = bcc;

}

/**

*

获取日期

* @return 日期

*/

public Date getDate() {

return date;

}

/**

*

设置日期

* @param date 日期

*/

public void setDate(Date date) {

this.date = date;

}

/**

*

获取邮件主题

* @return 邮件主题

*/

public String getSubject() {

return subject;

}

/**

*

设置邮件主题

* @param subject 邮件主题t

*/

public void setSubject(String subject) {

this.subject = subject;

}

/**

*

获取邮件正文

* @return 邮件正文

*/

public String getBody() {

return body;

}

/**

*

设置邮件正文

* @param body 邮件正文

*/

public void setBody(String body) {

this.body = body;

}

/**

*

获取附件列表

* @return 附件列表

*/

public List getAttachments() {

return attachments;

}

/**

*

Add attachment

* @param att

*/

public void addAttachment(Attachment att){

this.attachments.add(att);

}

/**

*

设置附件列表

* @param attachments 附件列表

*/

public void setAttachments(List attachments) {

this.attachments = attachments;

}

/**

*

获取邮件大小

* @return the 邮件大小

*/

public int getSize() {

return size;

}

/**

*

设置邮件大小

* @param size 邮件大小

*/

public void setSize(int size) {

this.size = size;

}

/**

*

获取邮件优先级

* @return 邮件优先级

*/

public int getPriority() {

return priority;

}

/**

*

设置邮件优先级

* @param priority 邮件优先级

*/

public void setPriority(int priority) {

this.priority = priority;

}

/**

*

获取邮件答复人列表

* @return ArrayList

*/

public List getReplyList() {

return replyList;

}

/**

*

设置邮件优先级

* @param list 答复人列表

*/

public void setReplyList(List list) {

this.replyList = list;

}

/**

*

自定义的MailMessage转换成JavaMail的Message

* @return JavaMail的Message

* @throws MessagingException

*/

protected Message toJavaMailMessage() throws Exception{

//设置邮件头信息

Message message = new MimeMessage(MailSender.getNormalSMTPSession());

message.setSubject(this.subject);

message.setSentDate(new Date());

message.setHeader("X-Priority", this.priority + "");

//FROM

message.setFrom(MailMessage.toAddress(this.from));

//REPLAY TO

message.setReplyTo(MailMessage.toAddressArray(this.replyList));

//TO

for(String str : this.to){

message.setRecipient(RecipientType.TO, MailMessage.toAddress(str));

}

//CC

for(String str : this.cc){

message.setRecipient(RecipientType.CC, MailMessage.toAddress(str));

}

//BCC

for(String str : this.bcc){

message.setRecipient(RecipientType.BCC, MailMessage.toAddress(str));

}

MimeMultipart mmp = null;

//以下为邮件体部分

if(this.attachments.size() == 0){

logger.trace("no attachmennts");

mmp = new MimeMultipart("alternative");

}else{

logger.trace("has attachmennts");

mmp = new MimeMultipart();

}

//正文

message.setContent(mmp);

MimeBodyPart part = new MimeBodyPart();

part.setText(this.body, "UTF-8");

mmp.addBodyPart(part);

//有附件则需要加上附件

if(this.attachments != null){

for(Attachment att : this.attachments){

DataSource source = null;

try{

source = new FileDataSource(att.getFilePath());

}catch(Exception e){

logger.error(e);

}

if(source == null){

logger.trace("cannot get file");

continue;

}

MimeBodyPart fileBodyPart = new MimeBodyPart();

fileBodyPart.setDataHandler(new DataHandler(source));

fileBodyPart.setFileName(MimeUtility.encodeText(att.getFileName(), "UTF-8", null));

mmp.addBodyPart(fileBodyPart);

}

}

return message;

}

/**

*

将自定义地址格式转换成javaMail中的Address

* @param addressStr

* @return

* @throws Exception

*/

private static Address toAddress(String addressStr) throws Exception{

if(StringUtils.isBlank(addressStr)){

return null;

}

//将全角的:替换成半角的:

addressStr = addressStr.replace(MailMessage.USUALLY_ERROR_SEPARATOR, MailMessage.SEPARATOR);

String personal = StringUtils.substringBefore(addressStr, MailMessage.SEPARATOR);

String address = StringUtils.substringAfter(addressStr, MailMessage.SEPARATOR);

if(StringUtils.isBlank(address)){

address = addressStr;

}

Address javaMailAddress = new InternetAddress(address , personal);

return javaMailAddress;

}

/**

*

将List中的地址列表转换成JavaMail Address数组

* @param list地址列表

* @return

* @throws Exception

*/

private static Address[] toAddressArray(List list) throws Exception {

List

addressList = new ArrayList
();

if(list == null){

return null;

}

for(String str : list){

addressList.add(MailMessage.toAddress(str));

}

return addressList.toArray(new Address[]{});

}

}

说明:

toJavaMailMessage方法将自定义的MailMessage转化为JavaMessage对象

toAddress方法将自定义的address(即String)转换为JavaMail的Address对象

以上两个方法作为对JavaMail依赖的解耦,让应用程序不需要直接依赖于javaMail。

自定义分隔符":"的作用是因为可以支持类似"UnclePeng:itworker@126.com"的方式,前者可以代表发件人,后者可以代表发件人地址。由于全角和半角的:区分并不显示,所以在调用的时候也要求能兼容这两个方式的写法。

3、MailSender.java

/*

*@# MailSender.java 4:33:54 PM Jul 17, 2009

*Copyright 2009 mozat, Inc. All rights reserved.

*/

package com.upeng.mysmtp;

import java.util.Properties;

import javax.mail.Message;

import javax.mail.Session;

import javax.mail.Transport;

import org.apache.commons.logging.Log;

import org.apache.commons.logging.LogFactory;

import com.upeng.commons.lang.StringUtils;

/**

*

邮件发送类

* @author Lucky

* 4:33:54 PM Jul 17, 2009

*/

public class MailSender {

private static final Log logger = LogFactory.getLog(MailSender.class);

//普通邮件发送session

private static final Session normalSMTPSession = Session.getInstance(new Properties());;

//SSL加密方式的邮件发送session

private static final Session sslSMTPSession = Session.getInstance(new Properties());

//TLS加密方式的邮件发送session

private static final Session tlsSMTPSession = Session.getInstance(new Properties());

static {

normalSMTPSession.getProperties().setProperty("mail.smtp.auth", "true");

normalSMTPSession.getProperties().setProperty("mail.smtps.auth", "true");

sslSMTPSession.getProperties().setProperty("mail.smtp.auth", "true");

sslSMTPSession.getProperties().setProperty("mail.smtps.auth", "true");

tlsSMTPSession.getProperties().setProperty("mail.smtp.auth", "true");

tlsSMTPSession.getProperties().setProperty("mail.smtps.auth", "true");

tlsSMTPSession.getProperties().setProperty("mail.smtp.starttls.enable", "true");

}

/**

*

发送邮件

* @param setting SMTP设置

* @param message 邮件

* @throws Exception

*/

public static void sendMail(SMTPSetting setting , MailMessage message) throws Exception{

if(StringUtils.isBlank(setting.getSmtpHost())){

throw new java.lang.IllegalArgumentException("SMTP host can't be blank!");

}

//默认用普通的session

Session mailSenderSession = normalSMTPSession;

//协议名

String protocolName = "smtp";

if(setting.getEnc().equals(SMTPSetting.SMTPEncrypt.SSL)){//SSL

mailSenderSession = sslSMTPSession;

protocolName = "smtps";

logger.trace("use SSL session");

}else if(setting.getEnc().equals(SMTPSetting.SMTPEncrypt.TLS)){//TLS

mailSenderSession = tlsSMTPSession;

logger.trace("user TLS session");

}else{

logger.trace("user NORMAL session");

}

logger.trace(String.format("protocol name is %s", protocolName));

//将MailMessage对象转换成JavaMail的Message对象

Message javaMailMessage = message.toJavaMailMessage();

long starttime = System.currentTimeMillis();

//连接服务器并发送邮件

Transport transport = mailSenderSession.getTransport(protocolName);

transport.connect(setting.getSmtpHost(), setting.getPort(), setting.getUserName() , setting.getPwd());

transport.sendMessage(javaMailMessage, javaMailMessage.getAllRecipients());

transport.close();

long endTime = System.currentTimeMillis();

logger.trace(String.format("send mail from %s to %s successfuly [%d milliseconds]", message.getForm(), message.getTo().get(0), endTime - (starttime)));

}

/**

* @return the normalSMTPSession

*/

public static Session getNormalSMTPSession() {

return normalSMTPSession;

}

/**

* @return the sslSMTPSession

*/

public static Session getSslSMTPSession() {

return sslSMTPSession;

}

/**

* @return the tlsSMTPSession

*/

public static Session getTlsSMTPSession() {

return tlsSMTPSession;

}

}

说明:在static块中初始化了3个session,根据SMTPSetting对象具体设置的是哪种加密方式调用不同的session来发送邮件

sendMail方法调用了JavaMail来发送邮件,是外部调用者与JavaMail彻底解耦。

测试:

126的邮箱,没有使用加密

public class Send126MailTest {

public static void main(String[] args) {

//SMTP设置,包括登录用户名、密码、SMTP主机地址和端口等信息

SMTPSetting setting = new SMTPSetting();

setting.setSmtpHost("smtp.126.com");

//setting.setSmtpHost("192.168.1.181");

setting.setUserName("itworker");

setting.setPwd("******");//换成你的密码

//邮件内容

MailMessage message = new MailMessage();

message.setForm("UnclePeng:itworker@126.com");//发件人

message.getTo().add("lucky.peng@mozat.com");//收件人

message.setSubject("this mail send by mysmtp");//主题

message.setBody("试试发送中文邮件能过mysmtp的哟,哈哈!!!");//正文

message.setPriority(1);//邮件优先级1为高,3为中,5为低

message.getReplyList().add("lucky.peng@mozat.com");

//附件

//Attachment att = new Attachment();

//att.setFileName("xxx.java");//附件名

//att.setFilePath("C:\\TestCase.java");//设置附件的路径

//message.addAttachment(att);

//发送邮件

try {

MailSender.sendMail(setting, message);

} catch (Exception e) {

e.printStackTrace();

}

}

}

gmail邮箱,使用ssl加密

public class SendGMailTest {

public static void main(String[] args) {

//SMTP设置,包括登录用户名、密码、SMTP主机地址和端口等信息

SMTPSetting setting = new SMTPSetting();

setting.setSmtpHost("smtp.gmail.com");

setting.setUserName("pengzhoushuo");

setting.setPwd("******");//换成你的密码

setting.setPort(465);

setting.setEnc(SMTPEncrypt.SSL);

//邮件内容

MailMessage message = new MailMessage();

message.setForm("pengzhoushuo:pengzhoushuo@gmail.com");//发件人

List toList = new ArrayList();//收件人列表

toList.add("lucky.peng@mozat.com.cn");

message.setTo(toList);

message.setSubject("this mail send by mysmtp");//主题

message.setBody("hello world!");//正文

message.setPriority(3);//邮件优先级1为高,3为中,5为低,默认为中

//发送邮件

try {

MailSender.sendMail(setting, message);

} catch (Exception e) {

e.printStackTrace();

}

}

}

HotMail邮箱,使用tls加密

public class SendHotMailTest {

public static void main(String[] args) {

//SMTP设置,包括登录用户名、密码、SMTP主机地址和端口等信息

SMTPSetting setting = new SMTPSetting();

setting.setSmtpHost("smtp.live.com");

setting.setUserName("pengzhoushuo@hotmail.com");//注意用户名必须是全称

setting.setPwd("******");//换成你的密码

setting.setEnc(SMTPEncrypt.TLS);//需要TLS支持

//邮件内容

MailMessage message = new MailMessage();

message.setForm("pengzhoushuo@yahoo.com");//发件人,原来HotMail还可以伪造发件人

List toList = new ArrayList();//收件人列表

toList.add("lucky.peng@mozat.com.cn");

message.setTo(toList);

message.setSubject("this mail send by mysmtp");//主题

message.setBody("hello world!");//正文

message.setPriority(3);//邮件优先级1为高,3为中,5为低,默认为中

//发送邮件

try {

MailSender.sendMail(setting, message);

} catch (Exception e) {

e.printStackTrace();

}

}

}

本节总结:

通过对JavaMail的封装,将调用者从具体的javaMail api中解耦出来,用简洁直观的代码来发送邮件,new一个SMTPSetting,再new一个Mailmessage,再调用MailSender的方法将前两个对象作为参数实现发送邮件。

另外这一系列的过程还可以通过log打印出执行步骤,方便开发调试。同时还支持简洁的方式发送附件,直接设置好附件的file path即可。另外本组件己经开源,svn地址是:http://mysmtp.googlecode.com/svn/trunk/

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值