熱點推薦:
您现在的位置: 電腦知識網 >> 編程 >> Java編程 >> Java核心技術 >> 正文

利用javamail和POP3、SMPT協議實現郵件的收發

2013-11-23 19:30:13  來源: Java核心技術 

  簡介
  SMTP 的全稱是Simple Mail Transfer Protocol即簡單郵件傳輸協議用於郵件發送SMTP 認證簡單地說就是要求必須在提供了賬戶名和密碼之後才可以登錄 SMTP 服務器
  POP(Post Office Protocol )協議允許電子郵件客戶端下載服務器上的郵件但是在客戶端的操作(如移動郵件標記已讀等)不會反饋到服務器上比如通過客戶端收取了郵箱中的封郵件並移動到其他文件夾郵箱服務器上的這些郵件是沒有同時被移動的
  而IMAP(Internet Mail Access Protocol)提供webmail 與電子郵件客戶端之間的雙向通信客戶端的操作都會反饋到服務器上對郵件進行的操作服務器上的郵件也會做相應的動作
  同時IMAP像POP那樣提供了方便的郵件下載服務讓用戶能進行離線閱讀IMAP提供的摘要浏覽功能可以讓你在閱讀完所有的郵件到達時間主題發件人大小等信息後才作出是否下載的決定此外IMAP 更好地支持了從多個不同設備中隨時訪問新郵件
  總之IMAP 整體上為用戶帶來更為便捷和可靠的體驗POP 更易丟失郵件或多次下載相同的郵件但 IMAP 通過郵件客戶端與webmail 之間的雙向同步功能很好地避免了這些問題
  注若在web郵箱中設置了保存到已發送使用客戶端POP服務發信時已發郵件也會自動同步到網頁端已發送文件夾內
  利用SMTP協議發送郵件
  package comlikeemail;
  import javaioFile;
  import javaioUnsupportedEncodingException;
  import javautilArrayList;
  import javautilProperties;
  import javaxactivationDataHandler;
  import javaxactivationDataSource;
  import javaxactivationFileDataSource;
  import javaxmailAuthenticator;
  import javaxmailBodyPart;
  import javaxmailMessage;
  import javaxmailMessagingException;
  import javaxmailMultipart;
  import javaxmailSession;
  import javaxmailTransport;
  import javaxmailinternetAddressException;
  import javaxmailinternetInternetAddress;
  import javaxmailinternetMimeBodyPart;
  import javaxmailinternetMimeMessage;
  import javaxmailinternetMimeMultipart;
  /**
  * @author like
  * @Email k
  * @CreateTime 下午::
  */
  public class SMTPSendTest {
  private static final int RECEIPT = ;
  private static final String attachmentDir = ;
  public static void sendEmail(Email emailInfo) throws UnsupportedEncodingException MessagingException {
  Properties props = new Properties()
  propsput(mailsmtphost emailInfogetSmtpServer())
  propsput(mailsmtpport emailInfogetSmtpPort())
  propsput(mailsmtpauth true
  Authenticator auth = new SMTPAuthenticator(emailInfogetUsername() emailInfogetPassword())
  Session session = SessiongetInstance(props auth)
  sessionsetDebug(false)
  Message msg = new MimeMessage(session)
  msgsetFrom(new InternetAddress(emailInfogetFrom() emailInfogetFromName()))
  msgsetRecipients(MessageRecipientTypeTO getEmailRecipient(emailInfogetTO()))
  msgsetRecipients(MessageRecipientTypeCC getEmailRecipient(emailInfogetCC()))
  msgsetRecipients(MessageRecipientTypeBCC getEmailRecipient(emailInfogetBCC()))
  if (emailInfogetReceipt() == RECEIPT) {
  msgsetHeader(DispositionNotificationTo emailInfogetFrom())
  }
  msgsetSubject(emailInfogetSubject())
  // 設置郵件內容(包括附件的HTML格式內容)
  msgsetContent(getMultipart(emailInfogetContent() attachmentDir emailInfogetAttachment()))
  msgsaveChanges()
  Transportsend(msg)
  }
  /**
  * 封裝郵件地址
  *
  * @param address
  * @return
  * @throws AddressException
  */
  private static InternetAddress[] getEmailRecipient(ArrayList<String> address) throws AddressException {
  int toLen = ;
  if (address != null) {
  toLen = addresssize()
  }
  InternetAddress[] addressTo = new InternetAddress[toLen];
  if (toLen != ) {
  String m_st_email = ;
  for (int i = ; i < toLen; i++) {
  m_st_email = (String) addressget(i)
  if (m_st_email != null)
  addressTo[i] = new InternetAddress(m_st_emailtrim())
  }
  }
  return addressTo;
  }
  private static Multipart getMultipart(String text String attachParentDir ArrayList<String> attachment) throws MessagingException {

  // 混合型郵件內容
  Multipart multi = new MimeMultipart(mixed// 混合MIME消息
  // 加入文本內容
  multiaddBodyPart(createContent(text))
  // 加入附件內容
  for (int i = ; i < attachmentsize() i++) {
  String attachmentI = (String) attachmentget(i)
  // 附件的真是存儲名稱
  String fileRealName = attachmentIsubstring(attachmentIindexOf(<) + trim()
  // 附件在郵件中的顯示名稱
  String fileShowName = attachmentIsubstring( attachmentIindexOf(>))
  multiaddBodyPart(createAttachment(fileShowName new File(attachParentDir + fileRealName)))// 嵌入附件
  }
  return multi;
  }
  /**
  * 郵件附件的處理
  *
  * @param fileName
  *            附件顯示名稱
  * @param file
  *            文件
  * @return javaxmailBodyPart(javaMail的郵件內容)
  * @throws MessagingException
  */
  private static BodyPart createAttachment(String fileName File file) throws MessagingException {
  BodyPart attach = new MimeBodyPart()
  DataSource ds = new FileDataSource(file)
  attachsetDataHandler(new DataHandler(ds))
  try {
  // 文件名重新編碼解決亂碼問題
  attachsetFileName(new String(fileNamegetBytes() ISO))
  } catch (UnsupportedEncodingException e) {
  eprintStackTrace()
  }
  return attach;
  }
  /**
  * 郵件文本內容的處理
  *
  * @param text
  *            文本內容
  * @return javaxmailBodyPart(javaMail的郵件內容)
  * @throws MessagingException
  */
  private static BodyPart createContent(String text) throws MessagingException {
  BodyPart content = new MimeBodyPart()
  // 郵件正文也是一種組合消息可以包含多個MimeBodyPart
  Multipart relate = new MimeMultipart(related
  BodyPart html = new MimeBodyPart()
  htmlsetContent(text text/html;charset=gbk
  relateaddBodyPart(html)
  contentsetContent(relate)
  return content;
  }
  }
  郵件內容結構圖
  三POP協議接受郵件
  package comlikeemail;
  import javautilProperties;
  import javaxmailAuthenticator;
  import javaxmailFlags;
  import javaxmailFolder;
  import javaxmailMessage;
  import javaxmailMessagingException;
  import javaxmailSession;
  import javaxmailStore;
  import comsunmailpopPOPFolder;
  /**
  * POP協議雖然相較IMAP協議有明顯劣勢但仍然使用廣泛而且並不是所有的郵件服務器都支持IMAP協議
  * @author like
  * @Email  k
  * @CreateTime 下午::
  */
  public class OPTest {
  public static void receive(String server int port String username String password boolean isDelete) throws MessagingException {
  Properties props = SystemgetProperties()
  Authenticator auth = new POPAuthenticator(username password)
  Session session = SessiongetInstance(props auth)
  sessionsetDebug(false)
  Store store = sessiongetStore(POP
  nnect(server port username password)
  //獲得收件箱
  POPFolder folder = (POPFolder) storegetFolder(INBOX
  try {
  //讀寫方式打開
  folderopen(FolderREAD_WRITE)
  } catch (MessagingException ex) {
  //制度方式打開
  folderopen(FolderREAD_ONLY)
  }
  // int totalMessages = foldergetMessageCount()
  Message m_message = null;
  Message[] msgs = foldergetMessages()
  for (int i = ; i < msgslength; i++) {
  m_message = msgs[i];
  String UID = foldergetUID(m_message)
  if (haveReceived(UID)) {
  // 插入數據庫
  // mailListadd(new RecvMailTask(m_message
  // p_st_attachmentParentDir UID))
  // 設置為已讀IMAP協議支持POP協議不支持該功能
  m_messagesetFlag(FlagsFlagSEEN true)
  // POP協議可以刪除
  m_messagesetFlag(FlagsFlagDELETED isDelete)
  }
  }
  }
  /**
  * POP協議的對郵件的操作和服務器不同步不能區分是否為已讀郵件 如果接收後不刪除服務器上的郵件下次仍然會接收該郵件
  * 服務器會給每一封郵件一個獨一無二的UID接收郵件時保存該UID到數據庫作為下次接收時是否已經接收過該郵件的依據
  * 有兩種方式)每次接收先從數據庫中讀取所有的UID接收時判斷是否包含當次接收郵件的UID
  * 優點是只讀一次數據庫缺點是讀出的UID數量可能會很多
  *  ()接收每一封郵件時把其UID作為參數查詢數據庫是否返回數據作為判斷依據
  *
  * @param UID
  * @return
  */
  private static boolean haveReceived(String UID) {
  //個人覺得第一種較好如果郵箱中郵件較多接收又較為頻繁那麼每次接收都會產生大量數據庫連接次數
  //第一種注意把取得的UID集放入到Set集合中用contains()方法直接判斷
  return true;
  }


From:http://tw.wingwit.com/Article/program/Java/hx/201311/26993.html
    推薦文章
    Copyright © 2005-2013 電腦知識網 Computer Knowledge   All rights reserved.