【java框架】SpringBoot(4)--SpringBoot實現非同步、郵件、定時任務
1.SpringBoot整合任務機制
1.1.SpringBoot實現非同步方法
日常開發中涉及很多介面與後端的互動響應,都不是同步的,基於SpringBoot為我們提供了註解方式實現非同步方法。使得前端的請求響應與後端的業務邏輯方法實現非同步執行。提升了客戶的體驗。不由得說一句,SpringBoot的封裝的確是精妙強大,以前需要多執行緒、Ajax實現非同步,而SpringBoot底層封裝之後,兩個註解就Over了!
①需要在SpringApplication執行類上開啟非同步,使用@EnableAsync:
@SpringBootApplication @EnableAsync //開啟非同步 public class SpringtestApplication { public static void main(String[] args) { SpringApplication.run(SpringtestApplication.class, args); } }
②同時在執行呼叫耗時的方法上加上@Async表示該方法是非同步方法:
@Service public class AsyncService { @Async public void execute(){ try { Thread.sleep(3000); //執行系統耗時任務 } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("任務執行成功!"); } }
③那麼執行Controller層的呼叫非同步方法時就會非同步去執行方法,得到響應“success”返回而同時非同步執行後臺耗時方法:
@RestController public class AsyncController { @Autowired private AsyncService service; @RequestMapping("/execute") public String executeTask(){ service.execute(); //非同步執行3s return "success"; //非同步返回結果 } }
1.2.SpringBoot實現郵件傳送
Spring Boot中傳送郵件具體的使用步驟如下
1、新增Starter模組依賴
2、新增Spring Boot配置(QQ/網易系/Gmail)
3、呼叫JavaMailSender介面傳送郵件
①在pom.xml中新增郵件傳送starter依賴:
<!--郵件傳送--> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-mail</artifactId> </dependency>
②對應QQ郵箱傳送,去QQ郵箱客戶端開啟POP3/SMTP服務,獲取授權碼:
③新增配置引數,在application.yml中配置郵箱傳送方式:
QQ郵箱:
# QQ郵箱配置 spring: mail: host: smtp.qq.com #傳送郵件伺服器 username: 241667****@qq.com #傳送郵件的郵箱地址 password: ************ #客戶端授權碼,不是郵箱密碼,這個在qq郵箱設定裡面自動生成的 properties.mail.smtp.port: 465 #埠號465或587 from: 241667****@qq.com # 傳送郵件的地址,和上面username一致 protocol: smtps #如果使用埠為465,將protocol的smtp改為smtps;配置檔案埠為587,則可以使用smtp。 #開啟加密驗證 properties.mail.smtp.ssl.enable: true
網易郵箱:
##網易系(126/163/yeah)郵箱配置 spring: mail: host: smtp.163.com #傳送郵件伺服器 username: hyfmail****@163.com #傳送郵件的郵箱地址 password: ************ #客戶端授權碼,不是郵箱密碼,網易的是自己設定的 properties.mail.smtp.port: 465 #465或者994 from: hyfmail****@163.com # 傳送郵件的地址,和上面username一致 properties.mail.smtp.ssl.enable: true default-encoding: utf-8
④編寫郵件傳送介面,實現類:
public interface IMailService { /** * 傳送文字郵件 * @param to 收件人 * @param subject 主題 * @param content 內容 */ void sendSimpleMail(String to, String subject, String content); /** * 傳送HTML郵件 * @param to 收件人 * @param subject 主題 * @param content 內容 */ public void sendHtmlMail(String to, String subject, String content); /** * 傳送帶附件的郵件 * @param to 收件人 * @param subject 主題 * @param content 內容 * @param filePath 附件 */ public void sendAttachmentsMail(String to, String subject, String content, String filePath); }
@Service public class MailServiceImpl implements IMailService { private final Logger logger = LoggerFactory.getLogger(this.getClass()); /** * Spring Boot 提供了一個傳送郵件的簡單抽象,使用的是下面這個介面,這裡直接注入即可使用 */ @Autowired private JavaMailSenderImpl mailSender; /** * 配置檔案中我的qq郵箱 */ @Value("${spring.mail.from}") private String from; @Override public void sendSimpleMail(String to, String subject, String content) { //建立SimpleMailMessage物件 SimpleMailMessage message = new SimpleMailMessage(); //郵件傳送人 message.setFrom(from); //郵件接收人 message.setTo(to); //郵件主題 message.setSubject(subject); //郵件內容 message.setText(content); //傳送郵件 mailSender.send(message); } /** * html郵件 * @param to 收件人 * @param subject 主題 * @param content 內容 */ @Override public void sendHtmlMail(String to, String subject, String content) { //獲取MimeMessage物件 MimeMessage message = mailSender.createMimeMessage(); MimeMessageHelper messageHelper; try { messageHelper = new MimeMessageHelper(message, true); //郵件傳送人 messageHelper.setFrom(from); //郵件接收人 messageHelper.setTo(to); //郵件主題 message.setSubject(subject); //郵件內容,html格式 messageHelper.setText(content, true); //傳送 mailSender.send(message); //日誌資訊 logger.info("郵件已經發送。"); } catch (MessagingException e) { logger.error("傳送郵件時發生異常!", e); } } /** * 帶附件的郵件 * @param to 收件人 * @param subject 主題 * @param content 內容 * @param filePath 附件 */ @Override public void sendAttachmentsMail(String to, String subject, String content, String filePath) { MimeMessage message = mailSender.createMimeMessage(); try { MimeMessageHelper helper = new MimeMessageHelper(message, true); helper.setFrom(from); helper.setTo(to); helper.setSubject(subject); helper.setText(content, true); FileSystemResource file = new FileSystemResource(new File(filePath)); String fileName = filePath.substring(filePath.lastIndexOf(File.separator)); helper.addAttachment(fileName, file); mailSender.send(message); //日誌資訊 logger.info("郵件已經發送。"); } catch (MessagingException e) { logger.error("傳送郵件時發生異常!", e); } } }
⑤編寫測試類:
@SpringBootTest(classes = {SendmailApplication.class}) @RunWith(SpringRunner.class) public class MailAppTest { @Autowired private IMailService mailService; /** * 測試傳送文字郵件 */ @Test public void testSendMail() { mailService.sendSimpleMail("[email protected]","主題:你好普通郵件","內容:第一封郵件"); } /** * 測試傳送Html郵件 */ @Test public void sendHtmlMail(){ mailService.sendHtmlMail("[email protected]","主題:你好html郵件","<h1>內容:第一封html郵件</h1>"); } @Test public void sendMimeContentMail(){ mailService.sendAttachmentsMail("[email protected]", "主題:你好複雜帶附件郵件", "<p style='color:red'>謝謝你的html郵件及問候~</p>", "E:\\Workspaces\\SpringBoot_Study\\springboot_test\\src\\main\\resources\\static\\1.jpg"); } }
1.3.定時任務
SpringBoot中執行定時任務主要用到有兩個重要介面與兩個任務排程的註解:
- TaskScheduler 任務排程者
- TaskExecutor 任務執行者
- @EnableScheduling 開啟定時功能的註解
- @Scheduled 用於在需要定時執行的方法上,表示在某一時刻定時執行
對應註解使用如下:
啟動類:
@SpringBootApplication @EnableAsync //開啟非同步 @EnableScheduling //開啟定時功能的註解 public class SpringtestApplication { public static void main(String[] args) { SpringApplication.run(SpringtestApplication.class, args); } }
啟動方法:
@Service public class ScheduleService { //定時執行註解@Scheduled,需要使用cron表示式進行定時任務執行 //表示每天下午13:43觸發 @Scheduled(cron = "0 43 13 ? * *") public void timeExecute(){ System.out.println("該任務被觸發執行了~~~"); } }
啟動SpringBoot專案,SpringBoot則會開啟定時任務執行並掃描方法上需要定時執行的註解,去定時執行相關的任務。
常用cron表示式如下:
0 0 2 1 * ? 表示在每月的1日的凌晨2點調整任務 0 15 10 ? * MON-FRI 表示週一到週五每天上午10:15執行作業 0 15 10 ? 6L 2002-2006 表示2002-2006年的每個月的最後一個星期五上午10:15執行作 0 0 10,14,16 * * ? 每天上午10點,下午2點,4點 0 0/30 9-17 * * ? 朝九晚五工作時間內每半小時 0 0 12 ? * WED 表示每個星期三中午12點 0 0 12 * * ? 每天中午12點觸發 0 15 10 ? * * 每天上午10:15觸發 0 15 10 * * ? 每天上午10:15觸發 0 15 10 * * ? 每天上午10:15觸發 0 15 10 * * ? 2005 2005年的每天上午10:15觸發 0 * 14 * * ? 在每天下午2點到下午2:59期間的每1分鐘觸發 0 0/5 14 * * ? 在每天下午2點到下午2:55期間的每5分鐘觸發 0 0/5 14,18 * * ? 在每天下午2點到2:55期間和下午6點到6:55期間的每5分鐘觸發 0 0-5 14 * * ? 在每天下午2點到下午2:05期間的每1分鐘觸發 0 10,44 14 ? 3 WED 每年三月的星期三的下午2:10和2:44觸發 0 15 10 ? * MON-FRI 週一至週五的上午10:15觸發 0 15 10 15 * ? 每月15日上午10:15觸發 0 15 10 L * ? 每月最後一日的上午10:15觸發 0 15 10 ? * 6L 每月的最後一個星期五上午10:15觸發 0 15 10 ? * 6L 2002-2005 2002年至2005年的每月的最後一個星期五上午10:15觸發 0 15 10 ? * 6#3 每月的第三個星期五上午10:15觸發
更多cron表示式請參閱:
https://www.jianshu.com/p/b4b8950fb987 《簡書--cron表示式》
https://www.matools.com/cron 《crom線上表示式生成器》
本部落格寫作參考文件相關:
https://www.jianshu.com/p/a7097a21b42d
https://blog.csdn.net/SixthMagnitude/article/details/114173570
https://www.bilibili.com/video/BV1PE411i7CV?p=52
https://www.jianshu.com/p/b4b8950fb987 《簡書--cron表示式》
https://www.matools.com/cron 《crom線上表示式生成器》
示例程式碼已上傳至Github地址:
https://github.com/devyf/SpringBoot_Study/tree/master/helloword_cr