EmailUtil.java 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278
  1. package com.fjhx.email.utils;
  2. import cn.hutool.core.util.ObjectUtil;
  3. import com.baomidou.mybatisplus.core.toolkit.IdWorker;
  4. import com.baomidou.mybatisplus.core.toolkit.StringPool;
  5. import com.fjhx.email.entity.dto.MailboxInfo;
  6. import com.fjhx.email.entity.dto.ObsFile;
  7. import com.fjhx.email.entity.dto.SendDto;
  8. import com.fjhx.email.entity.vo.MessageDetailVo;
  9. import com.fjhx.email.enums.MailFlagEnum;
  10. import com.sun.mail.imap.IMAPFolder;
  11. import com.sun.mail.imap.IMAPStore;
  12. import com.sun.mail.smtp.SMTPMessage;
  13. import com.sun.mail.util.MailSSLSocketFactory;
  14. import lombok.SneakyThrows;
  15. import javax.activation.DataHandler;
  16. import javax.mail.*;
  17. import javax.mail.internet.InternetAddress;
  18. import javax.mail.internet.MimeBodyPart;
  19. import javax.mail.internet.MimeMultipart;
  20. import javax.mail.internet.MimeUtility;
  21. import java.io.UnsupportedEncodingException;
  22. import java.net.URL;
  23. import java.util.*;
  24. public class EmailUtil {
  25. private static final Properties properties;
  26. private static final Session session;
  27. private static final HashMap<String, String> storeId = new HashMap<>();
  28. static {
  29. properties = new Properties();
  30. // 开启ssl
  31. properties.put("mail.imap.ssl.enable", true);
  32. // 套接字连接超时值(毫秒)。此超时由java.net.Socket实现。默认是无限超时。
  33. properties.put("mail.imap.connectiontimeout", 1000 * 60);
  34. // 套接字读取超时值(毫秒)。此超时由java.net.Socket实现。默认是无限超时。
  35. properties.put("mail.imap.timeout", 1000 * 60);
  36. // 套接字写超时值,单位为毫秒。此超时是通过使用java.util.concurrent实现的。
  37. // ScheduledExecutorService每个连接,调度线程在超时过期时关闭套接字。
  38. // 因此,使用此超时的开销是每个连接一个线程。默认是无限超时。
  39. properties.put("mail.imap.writetimeout", 1000 * 60);
  40. session = Session.getInstance(properties);
  41. storeId.put("name", "fjhx");
  42. storeId.put("version", "1.0");
  43. storeId.put("vendor", "fjhxClient");
  44. storeId.put("support-email", "fjhx@fjhx.com");
  45. }
  46. // @SneakyThrows
  47. // public static void main(String[] args) {
  48. // MailboxInfo mailboxInfo = new MailboxInfo();
  49. // mailboxInfo.setReceiveHost("imap.gmail.com");
  50. // mailboxInfo.setReceivePort(993);
  51. // mailboxInfo.setMailUser("y2428241269@gmail.com");
  52. // mailboxInfo.setMailPassword("upoujrquwweqtsuk");
  53. // IMAPStore imapStore = getIMAPStore(mailboxInfo);
  54. // System.out.println();
  55. // }
  56. // public static void main(String[] args) throws Exception {
  57. // ObsFile attachment = new ObsFile();
  58. // attachment.setFileUrl("https://os.winfaster.cn/fjhx/saas/GrandStar/2023/03/08/png/3092592f2d614d83854fad5e4c107143.png");
  59. // attachment.setFileName("board-1.png");
  60. // SendDto.Address address = new SendDto.Address();
  61. // address.setAddress("2428241269@qq.com");
  62. // SendDto sendDto = new SendDto();
  63. // sendDto.setTo(Collections.singletonList(address));
  64. // sendDto.setFileList(Collections.singletonList(attachment));
  65. // sendDto.setSubject("测试标题");
  66. // sendDto.setContent("测试内容");
  67. // sendMail("imap.qq.com", "2428241269@qq.com", "kdypajdrwfhtdihb", sendDto);
  68. // }
  69. /**
  70. * 获取imapStore
  71. * 993
  72. */
  73. public static IMAPStore getIMAPStore(MailboxInfo mailboxInfo) throws MessagingException {
  74. IMAPStore store = (IMAPStore) session.getStore("imap");
  75. store.connect(
  76. mailboxInfo.getReceiveHost(),
  77. mailboxInfo.getReceivePort(),
  78. mailboxInfo.getMailUser(),
  79. mailboxInfo.getMailPassword());
  80. store.id(storeId);
  81. return store;
  82. }
  83. /**
  84. * 获取收件人、抄送人、密送人、回复人
  85. */
  86. @SneakyThrows
  87. public static List<MessageDetailVo.MessageAddress> mailAddressList(Message message) {
  88. Address[] to = message.getRecipients(Message.RecipientType.TO);
  89. Address[] cc = message.getRecipients(Message.RecipientType.CC);
  90. Address[] bcc = message.getRecipients(Message.RecipientType.BCC);
  91. Address[] replyTo = message.getReplyTo();
  92. List<MessageDetailVo.MessageAddress> mailAddressList = new ArrayList<>();
  93. addMailAddressList(mailAddressList, to, 1);
  94. addMailAddressList(mailAddressList, cc, 2);
  95. addMailAddressList(mailAddressList, bcc, 3);
  96. addMailAddressList(mailAddressList, replyTo, 4);
  97. return mailAddressList;
  98. }
  99. /**
  100. * 获取标签
  101. */
  102. public static String getFlags(Flags flags) {
  103. if (flags == null) {
  104. return StringPool.EMPTY;
  105. }
  106. Flags.Flag[] systemFlags = flags.getSystemFlags();
  107. if (systemFlags.length == 0) {
  108. return StringPool.EMPTY;
  109. }
  110. StringJoiner stringJoiner = new StringJoiner(",");
  111. for (Flags.Flag systemFlag : systemFlags) {
  112. stringJoiner.add(MailFlagEnum.getType(systemFlag));
  113. }
  114. return stringJoiner.toString();
  115. }
  116. /**
  117. * 获取邮箱文件夹
  118. */
  119. public static List<String> getFolderNameList(IMAPStore imapStore) throws MessagingException {
  120. IMAPFolder folder = (IMAPFolder) imapStore.getDefaultFolder();
  121. Folder[] folders = folder.list();
  122. List<String> mailFolderList = new ArrayList<>();
  123. addMailFolderList(mailFolderList, folders);
  124. return mailFolderList;
  125. }
  126. /**
  127. * 发送邮件
  128. */
  129. public static void sendMail(String host, String user, String password, SendDto sendDto) throws Exception {
  130. // QQ存在一个特性设置SSL加密
  131. MailSSLSocketFactory sf = new MailSSLSocketFactory();
  132. sf.setTrustAllHosts(true);
  133. // 创建一个配置文件并保存
  134. Properties properties = new Properties();
  135. properties.put("mail.host", host);
  136. properties.put("mail.user", user);
  137. properties.put("mail.password", password);
  138. properties.put("mail.transport.protocol", "smtp");
  139. properties.put("mail.smtp.auth", true);
  140. properties.put("mail.smtp.ssl.enable", true);
  141. properties.put("mail.smtp.ssl.socketFactory.class", "javax.net.ssl.SSLSocketFactory");
  142. // 创建一个session对象
  143. Session session = Session.getInstance(properties);
  144. // 获取连接对象
  145. Transport transport = session.getTransport();
  146. // 创建邮件对象
  147. SMTPMessage mimeMessage = new SMTPMessage(session);
  148. // 邮件发送人
  149. mimeMessage.setFrom(new InternetAddress(user));
  150. List<SendDto.Address> to = sendDto.getTo();
  151. if (ObjectUtil.isNotEmpty(to)) {
  152. mimeMessage.setRecipients(Message.RecipientType.TO, getAddresses(to));
  153. }
  154. List<SendDto.Address> cc = sendDto.getCc();
  155. if (ObjectUtil.isNotEmpty(cc)) {
  156. mimeMessage.setRecipients(Message.RecipientType.CC, getAddresses(cc));
  157. }
  158. List<SendDto.Address> bcc = sendDto.getBcc();
  159. if (ObjectUtil.isNotEmpty(bcc)) {
  160. mimeMessage.setRecipients(Message.RecipientType.BCC, getAddresses(bcc));
  161. }
  162. List<SendDto.Address> replyTo = sendDto.getReplyTo();
  163. if (ObjectUtil.isNotEmpty(replyTo)) {
  164. mimeMessage.setReplyTo(getAddresses(replyTo));
  165. }
  166. // 邮件标题
  167. mimeMessage.setSubject(sendDto.getSubject());
  168. // 邮件内容大对象
  169. MimeMultipart mimeMultipart = new MimeMultipart();
  170. // 对象内添加正文
  171. BodyPart content = new MimeBodyPart();
  172. content.setContent(sendDto.getContent(), "text/html;charset=UTF-8");
  173. mimeMultipart.addBodyPart(content);
  174. // 对象内添加邮件
  175. List<ObsFile> fileList = sendDto.getFileList();
  176. if (ObjectUtil.isNotEmpty(fileList)) {
  177. for (ObsFile attachment : fileList) {
  178. DataHandler dataHandler = new DataHandler(new URL(attachment.getFileUrl()));
  179. MimeBodyPart mimeBodyPart = new MimeBodyPart();
  180. mimeBodyPart.setDataHandler(dataHandler);
  181. mimeBodyPart.setContentID(IdWorker.getIdStr());
  182. mimeBodyPart.setFileName(MimeUtility.encodeText(attachment.getFileName()));
  183. mimeMultipart.addBodyPart(mimeBodyPart);
  184. }
  185. }
  186. // 添加邮件内容
  187. mimeMessage.setContent(mimeMultipart);
  188. // 连接服务器
  189. transport.connect(host, user, password);
  190. // 发送邮件
  191. transport.sendMessage(mimeMessage, new Address[]{new InternetAddress(user)});
  192. // 关闭连接
  193. transport.close();
  194. }
  195. private static void addMailAddressList(List<MessageDetailVo.MessageAddress> mailAddressList, Address[] addresses, Integer type) {
  196. if (addresses == null) {
  197. return;
  198. }
  199. for (Address address : addresses) {
  200. InternetAddress internetAddress = (InternetAddress) address;
  201. MessageDetailVo.MessageAddress mailAddress = new MessageDetailVo.MessageAddress();
  202. mailAddress.setType(type);
  203. mailAddress.setEmail(internetAddress.getAddress());
  204. mailAddress.setPersonalName(internetAddress.getPersonal());
  205. mailAddressList.add(mailAddress);
  206. }
  207. }
  208. private static InternetAddress[] getAddresses(List<SendDto.Address> addressList) throws UnsupportedEncodingException {
  209. InternetAddress[] internetAddresses = new InternetAddress[addressList.size()];
  210. for (int i = 0; i < addressList.size(); i++) {
  211. InternetAddress internetAddress = new InternetAddress();
  212. internetAddress.setPersonal(addressList.get(i).getPersonal(), "utf-8");
  213. internetAddress.setAddress(addressList.get(i).getAddress());
  214. internetAddresses[i] = internetAddress;
  215. }
  216. return internetAddresses;
  217. }
  218. private static void addMailFolderList(List<String> mailFolderList, Folder[] folders) throws MessagingException {
  219. for (Folder folder : folders) {
  220. int type = folder.getType();
  221. if (type == 2) {
  222. addMailFolderList(mailFolderList, folder.list());
  223. } else if (type == 3) {
  224. mailFolderList.add(folder.getFullName());
  225. }
  226. }
  227. }
  228. }