五、使用JavaMail API 在明确了JavaMail API的核心部分如何工作后,本人将带领大家学习一些使用Java Mail API任务案例。
8 X1 r X0 v7 x: G, D/ R 1.发送邮件
9 \, | n7 {6 M) r+ e1 h5 c+ L 在获得了Session后,建立并填入邮件信息,然后发送它到邮件服务器。这便是使用Java Mail API发送邮件的过程,在发送邮件之前,我们需要设置SMTP服务器:通过设置Properties的mail.smtp.host属性。) ~8 b4 r% Z0 ^
String host = ...;String from = ...;String to = ...;// Get system propertiesProperties props = System.getProperties();// Setup mail serverprops.put("mail.smtp.host", host);// Get sessionSession session = Session.getDefaultInstance(props, null);// Define messageMimeMessage message = new MimeMessage(session);message.setFrom(new InternetAddress(from));message.addRecipient(Message.RecipientType.TO, new InternetAddress(to));message.setSubject("Hello JavaMail");message.setText("Welcome to JavaMail");// Send messageTransport.send(message);9 _% ~) U- A/ D. H2 v$ o! ~
由于建立邮件信息和发送邮件的过程中可能会抛出异常,所以我们需要将上面的代码放入到try-catch结构块中。
" g/ e! b7 `1 O2 ?' C4 j2 s1 g; U 2.接收邮件5 S5 w& W1 i9 g3 j
为了在读取邮件,我们获得了session,并且连接到了邮箱的相应store,打开相应的Folder,然后得到我们想要的邮件,当然别忘记了在结束时关闭连接。0 f% f F2 ]- l/ g" P+ D
String host = ...;String username = ...;String password = ...;// Create empty propertiesProperties props = new Properties();// Get sessionSession session = Session.getDefaultInstance(props, null);// Get the storeStore store = session.getStore("pop3");store.connect(host, username, password);// Get folderFolder folder = store.getFolder("INBOX");folder.open(Folder.READ_ONLY);// Get directoryMessage message[] = folder.getMessages();for (int i=0, n=message.length; i
$ d8 |2 b0 C6 g% I! i4 q 上面的代码所作的是从邮箱中读取每个邮件,并且显示邮件的发信人地址和主题。从技术角度讲,这里存在着一个异常的可能:当发信人地址为空时,getFrom()[0]将抛出异常。
7 u6 ]+ |$ Z& I9 q* @ 下面的代码片断有效的说明了如何读取邮件内容,在显示每个邮件发信人和主题后,将出现用户提示从而得到用户是否读取该邮件的确认,如果输入YES的话,我们可用Message.writeTo(java.io.OutputStream os)方法将邮件内容输出到控制台上,关于Message.writeTo()的具体用法请看JavaMail API。8 C* d- w7 ?! A$ z6 v
BufferedReader reader = new BufferedReader ( new InputStreamReader(System.in));// Get directoryMessage message[] = folder.getMessages();for (int i=0, n=message.length; i
! i9 Y, ~; G, t& `6 i, [1 x* E 窗体底端( N3 e& R: y" a- E9 O
B.读取邮件中的附件. {+ J) f3 S6 T2 p% T- V& T
读取邮件中的附件的过程要比发送它的过程复杂一点。因为带有附件的邮件是多部分组成的,我们必须处理每一个部分获得邮件的内容和附件。
: _( O1 A8 r- f% T9 u8 O 但是如何辨别邮件信息内容和附件呢?Sun在Part类(BodyPart类实现的接口类)中提供了getDisposition()方法让开发者获得邮件体部分的部署类型,当该部分是附件时,其返回之将是Part.ATTACHMENT。但附件也可以没有部署类型的方式存在或者部署类型为Part.INLINE,无论部署类型为Part.ATTACHMENT还是Part.INLINE,我们都能把该邮件体部分导出保存。
m$ }1 O; K# o! B( _& @# Q1 } Multipart mp = (Multipart)message.getContent();for (int i=0, n=multipart.getCount(); i9 [# m/ X [, @7 }$ I* z: V
下列代码中使用了saveFile方法是自定义的方法,它根据附件的文件名建立一个文件,如果本地磁盘上存在名为附件的文件,那么将在文件名后增加数字表示区别。然后从邮件体中读取数据写入到本地文件中(代码省略)。6 T3 Q2 w' X' ~, w. h7 B: P& a+ D
// from saveFile()File file = new File(filename);for (int i=0; file.exists(); i++) { file = new File(filename+i);}( z$ N3 V" c `
以上是邮件体部分被正确设置的简单例子,如果邮件体部分的部署类型为null,那么我们通过获得邮件体部分的MIME类型来判断其类型作相应的处理,代码结构框架如下:1 Q$ g4 d. H7 g5 _/ g6 x# S
if (disposition == null) { // Check if plain MimeBodyPart mbp = (MimeBodyPart)part; if (mbp.isMimeType("text/plain")) { // Handle plain } else { // Special non-attachment cases here of // image/gif, text/html, ... }...}
0 [; J' ~7 e: f: l 8.处理HTML邮件
8 ?- y' X* G+ k" s 前面的例子中发送的邮件都是以文本为内容的(除了附件),下面将介绍如何接收和发送基于HTML的邮件。
% U) Y. V3 d O2 B+ i$ i! Y7 L A.发送HTML邮件2 u- t6 C4 e& e2 E7 S: _2 a
假如我们需要发送一个HTML文件作为邮件内容,并使邮件客户端在读取邮件时获取相关的图片或者文字的话,只要设置邮件内容为html代码,并设置内容类型为text/html即可:
2 X3 D1 ^9 [9 U" U* x- [ String htmlText = "! p, g8 k6 F! ]
Hello8 J' ]8 @5 Z9 ~$ E4 @
" + "";message.setContent(htmlText, "text/html"));
- V$ u7 _2 i/ r4 T! q+ [0 M 请注意:这里的图片并不是在邮件中内嵌的,而是在URL中定义的。邮件接收者只有在线时才能看到。, `; l8 C5 A4 Q: d, t$ v
在接收邮件时,如果我们使用JavaMail API接收邮件的话是无法实现以HTML方式显示邮件内容的。因为JavaMail API邮件内容视为二进制流。所以要显示HTML内容的邮件,我们必须使用JEditorPane或者第三方HTML展现组件。
2 Q% T# W# X- r- ]' r% [ 以下代码显示了如何使用JEditorPane显示邮件内容:5 a N; W* c6 f' y H
if (message.getContentType().equals("text/html")) { String content = (String)message.getContent(); JFrame frame = new JFrame(); JEditorPane text = new JEditorPane("text/html", content); text.setEditable(false); JScrollPane pane = new JScrollPane(text); frame.getContentPane().add(pane); frame.setSize(300, 300); frame.setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE); frame.show();} |