SpringBoot:網站的郵件發送與異步任務

前言:網站的異步任務常常應用在耗時的請求中,像郵件發送這種需要網絡請求的都屬於耗時任務,應當開啓多線程處理而不是讓客戶等待---最終目的實現個人網站的異步發送郵件效果

1.準備工作SpringBoot項目

  • 導入相關啓動器 web,thymeleaf,mail...
   <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-thymeleaf</artifactId>
        </dependency>
        <dependency>
            <groupId>org.thymeleaf.extras</groupId>
            <artifactId>thymeleaf-extras-java8time</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <!--郵件發送-->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-mail</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

2.配置SpringBoot mail相關屬性

spring.mail.username=xxxxx 郵箱
spring.mail.password=xxxxxxx 開啓POP3/SMTP服務 密碼
spring.mail.host=smtp.qq.com

#開啓加密驗證
spring.mail.properties.mail.smtp.enable=true

3.測試發送郵件的相關接口

  • 自動裝配獲取 JavaMailSenderImpl實例
  • 嘗試發送簡單郵件
  • 嘗試方法帶附件和富文本的複雜郵件
  @Autowired
    JavaMailSenderImpl mailSender;
    @Test
    void contextLoads() {

        SimpleMailMessage mailMessage = new SimpleMailMessage();

        // 主題
        mailMessage.setSubject("你好呀");

        // 內容
        mailMessage.setText("Java從入門到精通");

        // 收件人
        mailMessage.setTo("郵箱");

        // 發送人
        mailMessage.setFrom("郵箱");
        mailSender.send(mailMessage);
    }

    @Test
    public void mailF() throws MessagingException {
        // 複雜的郵件
        MimeMessage mimeMessage = mailSender.createMimeMessage();

        // 組裝
        MimeMessageHelper helper = new MimeMessageHelper(mimeMessage,true);

        helper.setSubject("xxx你好~");
        helper.setText("<h3 style=\"color: cyan\">Hello HT</h3>",true);

        // 添加附件
        helper.addAttachment("1.jpg",new File("C:\\Users\\lenovo\\Desktop\\截圖\\1.jpg"));

        // 收件人
        helper.setTo("郵箱");

        // 發送人
        helper.setFrom("郵箱");

        mailSender.send(mimeMessage);

    }

4.重構自己的郵件服務類(可直接拷貝用於自己的項目中)

@Service
public class SendMailService {

    @Autowired
    JavaMailSenderImpl mailSender;

    /**
     * 重構的郵件發送方法
     * @param multipartOpen 是否開啓複雜郵件支持:如果爲true 支持備選文本,行內元素和附件
     * @param subject 郵件主題
     * @param hText 郵件內容 富文本或文本
     * @param htmlOpean 內容支持富文本識別
     * @param attachmentFileName 附件名
     * @param pathname 附件路徑
     * @param from 發送者
     * @param to 收件者
     * @throws MessagingException
     */
    public void sendmimeMail(Boolean multipartOpen,String subject,String hText,Boolean htmlOpean,
                         String attachmentFileName,String pathname,String from,String to)
            throws MessagingException {
        // 複雜的郵件
        MimeMessage mimeMessage = mailSender.createMimeMessage();
        // 組裝
        MimeMessageHelper helper = new MimeMessageHelper(mimeMessage,multipartOpen);
        helper.setSubject(subject);
        helper.setText(hText,htmlOpean);
        // 添加附件
        helper.addAttachment(attachmentFileName,new File(pathname));
        // 發送人
        helper.setFrom(from);
        // 收件人
        helper.setTo(to);
        mailSender.send(mimeMessage);
    }


    /**
     * 發送簡單郵件
     * @param subject 主題
     * @param text 文本
     * @param from 發送者
     * @param to 收件人
     */
    public void sendMailMessage(String subject,String text,String from,String to){
        SimpleMailMessage mailMessage = new SimpleMailMessage();
        // 主題
        mailMessage.setSubject(subject);
        // 內容
        mailMessage.setText(text);
        // 發送人
        mailMessage.setFrom(from);
        // 收件人
        mailMessage.setTo(to);

        mailSender.send(mailMessage);
    }
}

5.簡單的前端頁面準備(BootStrap組件)

    <div style="position: center">
        <form th:action="@{/mail/send}">
            <div class="form-group">
                <label for="from">發件人(郵箱)</label>
                <input type="text" class="form-control" name="from" id="from" placeholder="Email">
            </div>
            <div class="form-group">
                <label for="to">收件人(郵箱)</label>
                <input type="text" class="form-control" name="to" id="to" placeholder="Email">
            </div>

            <div class="form-group">
                <label for="subject">郵件主題: </label>
                <input type="text" class="form-control" name="subject" id="subject" placeholder="主題...">
            </div>

            <div class="form-group">
                <label for="text">郵件內容:</label>
                <textarea class="form-control" id="text" name="text" rows="10"></textarea>
            </div>
            <div class="form-group">
                <label for="exampleInputFile">附件</label>
                <input type="file" id="exampleInputFile">
                <p class="help-block">Example block-level help text here.</p>
            </div>

            <div class="checkbox">
                <label>
                    <input type="checkbox" name="multipartOpen" value="open"> 上傳附件
                </label>
            </div>

            <button type="submit" class="btn btn-primary">發送郵件</button>
        </form>
    </div>

6.發送郵件相關Controller

  • 注入郵件服務實例
  • 響應表單發送郵件請求
@Controller
@RequestMapping("/mail")
public class SendMailController {
    @Autowired
    SendMailService mailService;

    @ResponseBody
    @RequestMapping("/send")
    public String sendMail(@RequestParam("from") String from,
                           @RequestParam("to") String to,
                           @RequestParam("subject") String subject,
                           @RequestParam("text") String text,
                           HttpServletRequest request){
        String open = request.getParameter("multipartOpen");

        if (null != open){
           // mailService.sendmimeMail(multipartOpen);
            System.out.println(open);
        }else {
            // 簡單郵件處理
            mailService.sendMailMessage(subject, text, from, to);
        }

        return "Send Email OK!";
    }
}

7.展示效果

8.聊聊異步任務與實現

  • 異步任務的本質:調用線程池,多線程後臺處理任務

  • 優勢:在處理耗時任務時,可讓用戶先做其它請求而非等待

  • SpringBoot處理異步任務很簡單:
    1.註解標記任務爲異步 @Async 2. 開啓異步任務處理@EnableAsync // 開啓異步任務

  • 標記異步處理任務,調用時自動開啓多線程

 @Async
    public void sendmimeMail(Boolean multipartOpen,String subject,String hText,Boolean htmlOpean,
                         String attachmentFileName,String pathname,String from,String to)
            throws MessagingException {
        // 複雜的郵件
        MimeMessage mimeMessage = mailSender.createMimeMessage();
        // 組裝
        MimeMessageHelper helper = new MimeMessageHelper(mimeMessage,multipartOpen);
        helper.setSubject(subject);
        helper.setText(hText,htmlOpean);
        // 添加附件
        helper.addAttachment(attachmentFileName,new File(pathname));
        // 發送人
        helper.setFrom(from);
        // 收件人
        helper.setTo(to);
        mailSender.send(mimeMessage);
    }


    /**
     * 發送簡單郵件
     * @param subject 主題
     * @param text 文本
     * @param from 發送者
     * @param to 收件人
     */
    @Async
    public void sendMailMessage(String subject,String text,String from,String to){
        SimpleMailMessage mailMessage = new SimpleMailMessage();
        // 主題
        mailMessage.setSubject(subject);
        // 內容
        mailMessage.setText(text);
        // 發送人
        mailMessage.setFrom(from);
        // 收件人
        mailMessage.setTo(to);

        mailSender.send(mailMessage);
    }
  • 主函數入口處開啓異步處理
@EnableAsync // 開啓異步任務
@SpringBootApplication
public class SpringbootSwaggerApplication {

    public static void main(String[] args) {
        SpringApplication.run(SpringbootSwaggerApplication.class, args);
    }

}

9.體驗異步郵件發送

            System.out.println("開始異步發送郵件...");
            mailService.sendMailMessage(subject, text, from, to);
            System.out.println("發送成功!");
  • 在發送過程中可以隨意訪問網站,如同瞬間發送完成
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章