ruoyi-api/ruoyi-api-account/src/main/java/com/ruoyi/account/api/dto/UploadPdfDTO.java
File was renamed from ruoyi-service/ruoyi-order/src/main/java/com/ruoyi/order/dto/UploadPdfDTO.java @@ -1,4 +1,4 @@ package com.ruoyi.order.dto; package com.ruoyi.account.api.dto; import io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; @@ -17,5 +17,7 @@ public Long id; @ApiModelProperty("文件路径") private String invoiceUrl; @ApiModelProperty("邮件地址") private String mailBox; } ruoyi-api/ruoyi-api-account/src/main/java/com/ruoyi/account/api/factory/AppUserFallbackFactory.java
@@ -2,6 +2,7 @@ import com.ruoyi.account.api.dto.GiveVipDto; import com.ruoyi.account.api.dto.SendMessageDTO; import com.ruoyi.account.api.dto.UploadPdfDTO; import com.ruoyi.account.api.feignClient.AppUserClient; import com.ruoyi.account.api.model.TAppCoupon; import com.ruoyi.account.api.model.TAppUser; @@ -36,6 +37,11 @@ } @Override public R uploadPdf(UploadPdfDTO dto) { return R.fail("开票发送邮件失败:"+throwable.getMessage()); } @Override public R<TAppUser> getUserById(Long id) { return R.fail("根据id查询用户失败:"+throwable.getMessage()); } ruoyi-api/ruoyi-api-account/src/main/java/com/ruoyi/account/api/feignClient/AppUserClient.java
@@ -2,6 +2,7 @@ import com.ruoyi.account.api.dto.GiveVipDto; import com.ruoyi.account.api.dto.SendMessageDTO; import com.ruoyi.account.api.dto.UploadPdfDTO; import com.ruoyi.account.api.model.TAppCoupon; import com.ruoyi.account.api.model.TAppUser; import com.ruoyi.account.api.model.TAppUserAddress; @@ -24,6 +25,9 @@ @ApiOperation(value = "管理后台-根据手机号查询用户ids", tags = {"管理后台-活动费用统计"}) @PostMapping(value = "/t-app-user/user/getUserIdsByPhone") public R<List<Long>> getUserIdsByPhone(@RequestParam("phone") String phone); @ApiOperation(value = "管理后台-开票发送邮件", tags = {"管理后台-开票发送邮件"}) @PostMapping(value = "/t-app-user/uploadPdf") public R uploadPdf(@RequestBody UploadPdfDTO dto); /** * 根据用户id查询用户信息 ruoyi-service/ruoyi-account/pom.xml
@@ -15,6 +15,17 @@ </description> <dependencies> <!--网易邮件--> <dependency> <groupId>javax.mail</groupId> <artifactId>javax.mail-api</artifactId> <version>1.6.2</version> </dependency> <dependency> <groupId>com.sun.mail</groupId> <artifactId>jakarta.mail</artifactId> <version>1.6.5</version> </dependency> <dependency> <groupId>com.ruoyi</groupId> <artifactId>ruoyi-api-order</artifactId> ruoyi-service/ruoyi-account/src/main/java/com/ruoyi/account/controller/TAppUserController.java
@@ -49,17 +49,31 @@ import com.ruoyi.other.api.feignClient.VipClient; import com.ruoyi.system.api.model.LoginUser; import com.ruoyi.system.api.model.LoginUserApplet; import com.sun.xml.internal.messaging.saaj.packaging.mime.internet.MimeUtility; import io.swagger.annotations.ApiOperation; import lombok.extern.slf4j.Slf4j; import org.apache.commons.compress.utils.IOUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.data.redis.core.RedisTemplate; import org.springframework.validation.annotation.Validated; import org.springframework.web.bind.annotation.*; import org.springframework.web.client.RestTemplate; import javax.activation.DataHandler; import javax.activation.FileDataSource; import javax.annotation.Resource; import javax.mail.*; import javax.mail.internet.InternetAddress; import javax.mail.internet.MimeBodyPart; import javax.mail.internet.MimeMessage; import javax.mail.internet.MimeMultipart; import javax.servlet.http.HttpServletRequest; import java.io.File; import java.io.FileOutputStream; import java.io.InputStream; import java.io.UnsupportedEncodingException; import java.math.BigDecimal; import java.net.URL; import java.time.Duration; import java.time.LocalDate; import java.time.LocalDateTime; @@ -134,7 +148,109 @@ @Resource private GiveVipUtil giveVipUtil; /** * 远程调用 发送邮件 * @return */ @PostMapping(value = "/uploadPdf") public R uploadPdf(@RequestBody UploadPdfDTO dto) { // 发送邮箱 // 收件人电子邮箱,TODO 换成自己的收件箱 String to = dto.getMailBox(); // 发件人电子邮箱,TODO 换成自己的发件箱 String from = "13281306557@163.com"; // 指定发送邮件的主机为 String host = "smtp.163.com"; Properties properties = new Properties(); properties.put("mail.smtp.host", "smtp.163.com"); properties.put("mail.smtp.socketFactory.port", "465"); properties.put("mail.smtp.socketFactory.class", "javax.net.ssl.SSLSocketFactory"); properties.put("mail.smtp.auth", "true"); properties.put("mail.smtp.port", "465"); properties.put("mail.smtp.ssl.enable", "true"); // 明确开启SSL // 获取默认session对象 Session session = Session.getDefaultInstance(properties,new Authenticator(){ @Override public javax.mail.PasswordAuthentication getPasswordAuthentication() { //发件人邮件用户名、授权码,换成自己的发件箱及授权码 return new PasswordAuthentication("13281306557@163.com", "NUSdxDQqadYvVek2"); } }); try{ // 创建默认的 MimeMessage 对象 MimeMessage message = new MimeMessage(session); // Set From,设置发件人 InternetAddress fromMail = new InternetAddress(from); //设置发件人名称,TODO 换成自己的发件箱 fromMail.setPersonal(MimeUtility.encodeText("明星电力<13281306557@163.com>")); message.setFrom(fromMail); // Set To: 设置收件人 InternetAddress toMail = new InternetAddress(to); // TODO 换成自己的收件箱 InternetAddress toMail2 = new InternetAddress(to); //发多个邮箱 Address[] allRecipients = {toMail, toMail2}; message.setRecipients(Message.RecipientType.TO, allRecipients); // Set Subject: 邮件主体 message.setSubject("明星电力"); // 设置消息体 message.setSentDate(new Date()); javax.mail.internet.MimeMultipart msgMultipart = new MimeMultipart("mixed"); // 指定为混合关系 message.setContent(msgMultipart); // 邮件信息组装 //组装的顺序非常重要,一定要先组装文本域,再组装文件 javax.mail.internet.MimeBodyPart htmlPart = new javax.mail.internet.MimeBodyPart(); // 组装内容 htmlPart.setContent("开票", "text/html;charset=UTF-8"); msgMultipart.addBodyPart(htmlPart); // 组装附件 javax.mail.internet.MimeBodyPart filePart = new MimeBodyPart(); String imageUrl = dto.getInvoiceUrl(); try { // 下载数据 URL url = new URL(imageUrl); InputStream inputStream = url.openStream(); byte[] imageBytes = IOUtils.toByteArray(inputStream); // 创建临时文件 // 截取imageUrl后缀名 String fileExtension = imageUrl.substring(imageUrl.lastIndexOf(".")); File tempFile = File.createTempFile("tempImage", fileExtension); try (FileOutputStream fos = new FileOutputStream(tempFile)) { fos.write(imageBytes); } // 创建 FileDataSource FileDataSource fileDataSource = new FileDataSource(tempFile); System.out.println("FileDataSource created: " + fileDataSource.getName()); // 如果需要,可以使用 DataHandler 进行进一步处理 DataHandler dh = new DataHandler(fileDataSource); // 清理:删除临时文件(如果不再需要) tempFile.deleteOnExit(); // 可根据需要保留或删除 filePart.setDataHandler(dh); // 附件区别内嵌内容的一个特点是有文件名,为防止中文乱码要编码 filePart.setFileName(MimeUtility.encodeText(dh.getName())); msgMultipart.addBodyPart(filePart); message.saveChanges(); //发送 //Transport.send(message, message.getAllRecipients()); Transport.send(message); System.out.println("发送成功"); } catch (Exception e) { e.printStackTrace(); } }catch (MessagingException | UnsupportedEncodingException mex) { mex.printStackTrace(); } catch (Exception e) { e.printStackTrace(); } return R.ok(); } /** * 远程调用 积分兑换订单 退款回退积分 * @return ruoyi-service/ruoyi-order/src/main/java/com/ruoyi/order/controller/TOrderInvoiceController.java
@@ -3,6 +3,8 @@ import cn.afterturn.easypoi.excel.ExcelExportUtil; import cn.afterturn.easypoi.excel.entity.ExportParams; import com.ruoyi.account.api.dto.UploadPdfDTO; import com.ruoyi.account.api.feignClient.AppUserClient; import com.ruoyi.common.core.utils.DateUtils; import com.ruoyi.common.core.utils.WebUtils; import com.ruoyi.common.core.web.domain.AjaxResult; @@ -56,6 +58,8 @@ @Resource private TokenService tokenService; @Resource private AppUserClient appUserClient; @@ -78,20 +82,18 @@ public static void main(String[] args) { // 发送邮箱 // 收件人电子邮箱,TODO 换成自己的收件箱 String to = "619865809@qq.com"; String to = "443237572@qq.com"; // 发件人电子邮箱,TODO 换成自己的发件箱 String from = "13281306557@163.com"; // 指定发送邮件的主机为 String host = "smtp.163.com"; // 获取系统属性 Properties properties = new Properties(); // 设置邮件服务器 properties.setProperty("mail.smtp.host", host); // 邮件发送协议 properties.setProperty("mail.transport.protocol", "smtp"); //是否启用调试模式(启用调试模式可打印客户端与服务器交互过程时一问一答的响应消息) properties.setProperty("mail.debug","true"); properties.setProperty("mail.smtp.auth", "true"); properties.put("mail.smtp.host", "smtp.163.com"); properties.put("mail.smtp.socketFactory.port", "465"); properties.put("mail.smtp.socketFactory.class", "javax.net.ssl.SSLSocketFactory"); properties.put("mail.smtp.auth", "true"); properties.put("mail.smtp.port", "465"); properties.put("mail.smtp.ssl.enable", "true"); // 明确开启SSL // 获取默认session对象 Session session = Session.getDefaultInstance(properties,new Authenticator(){ @Override @@ -182,100 +184,8 @@ orderInvoice.setInvoiceUrl(dto.getInvoiceUrl()); orderInvoice.setStatus(3); orderInvoiceService.updateById(orderInvoice); // 发送邮箱 // 收件人电子邮箱,TODO 换成自己的收件箱 String to = orderInvoice.getMailbox(); // 发件人电子邮箱,TODO 换成自己的发件箱 String from = "13281306557@163.com"; // 指定发送邮件的主机为 String host = "smtp.163.com"; Properties properties = new Properties(); properties.put("mail.smtp.host", "smtp.163.com"); properties.put("mail.smtp.socketFactory.port", "465"); properties.put("mail.smtp.socketFactory.class", "javax.net.ssl.SSLSocketFactory"); properties.put("mail.smtp.auth", "true"); properties.put("mail.smtp.port", "465"); properties.put("mail.smtp.ssl.enable", "true"); // 明确开启SSL // 获取默认session对象 Session session = Session.getDefaultInstance(properties,new Authenticator(){ @Override public PasswordAuthentication getPasswordAuthentication() { //发件人邮件用户名、授权码,换成自己的发件箱及授权码 return new PasswordAuthentication("13281306557@163.com", "NUSdxDQqadYvVek2"); } }); try{ // 创建默认的 MimeMessage 对象 MimeMessage message = new MimeMessage(session); // Set From,设置发件人 InternetAddress fromMail = new InternetAddress(from); //设置发件人名称,TODO 换成自己的发件箱 fromMail.setPersonal(MimeUtility.encodeText("明星电力<13281306557@163.com>")); message.setFrom(fromMail); // Set To: 设置收件人 InternetAddress toMail = new InternetAddress(to); // TODO 换成自己的收件箱 InternetAddress toMail2 = new InternetAddress(to); //发多个邮箱 Address[] allRecipients = {toMail, toMail2}; message.setRecipients(Message.RecipientType.TO, allRecipients); // Set Subject: 邮件主体 message.setSubject("明星电力"); // 设置消息体 message.setSentDate(new Date()); // 指定为混合关系 MimeMultipart msgMultipart = new MimeMultipart("mixed"); message.setContent(msgMultipart); // 邮件信息组装 //组装的顺序非常重要,一定要先组装文本域,再组装文件 MimeBodyPart htmlPart = new MimeBodyPart(); // 组装内容 htmlPart.setContent("开票", "text/html;charset=UTF-8"); msgMultipart.addBodyPart(htmlPart); // 组装附件 MimeBodyPart filePart = new MimeBodyPart(); String imageUrl = dto.getInvoiceUrl(); try { // 下载数据 URL url = new URL(imageUrl); InputStream inputStream = url.openStream(); byte[] imageBytes = IOUtils.toByteArray(inputStream); // 创建临时文件 // 截取imageUrl后缀名 String fileExtension = imageUrl.substring(imageUrl.lastIndexOf(".")); File tempFile = File.createTempFile("tempImage", fileExtension); try (FileOutputStream fos = new FileOutputStream(tempFile)) { fos.write(imageBytes); } // 创建 FileDataSource FileDataSource fileDataSource = new FileDataSource(tempFile); System.out.println("FileDataSource created: " + fileDataSource.getName()); // 如果需要,可以使用 DataHandler 进行进一步处理 DataHandler dh = new DataHandler(fileDataSource); // 清理:删除临时文件(如果不再需要) tempFile.deleteOnExit(); // 可根据需要保留或删除 filePart.setDataHandler(dh); // 附件区别内嵌内容的一个特点是有文件名,为防止中文乱码要编码 filePart.setFileName(MimeUtility.encodeText(dh.getName())); msgMultipart.addBodyPart(filePart); message.saveChanges(); //发送 //Transport.send(message, message.getAllRecipients()); Transport.send(message); System.out.println("发送成功"); } catch (Exception e) { e.printStackTrace(); } }catch (MessagingException | UnsupportedEncodingException mex) { mex.printStackTrace(); } catch (Exception e) { e.printStackTrace(); } dto.setMailBox(orderInvoice.getMailbox()); appUserClient.uploadPdf(dto); return AjaxResult.success(); }