SpringBoot @Async 非同步處理商務邏輯和發簡訊邏輯

來源:互聯網
上載者:User

標籤:使用者   data   sap   imp   ant   spring   cat   理由   logger   

有個業務情境,業務資料審核通過後需要給使用者發簡訊,發簡訊過程比較耗時,可能需要幾秒甚至十幾秒,因此使用非同步發簡訊

使用了註解@Async來實現:

1.SpringApplication啟用註解@EnableAsync

@SpringBootApplication@ImportResource(locations = { "classpath:/spring/spring-*.xml" })@EnableTransactionManagement(proxyTargetClass=true)@EnableScheduling@EnableAutoConfiguration(exclude = { FreeMarkerAutoConfiguration.class })@EnableSwagger2@ServletComponentScan(basePackages="com.xx")@EnableMongoRepositories(basePackages = "com.xx.xx.xx.xx")@EnableAsyncpublic class IemsApplication {public static void main(String[] args) {SpringApplication.run(IemsApplication.class, args);}    ...

2.在業務層(@Service)具體的審核方法上添加註釋@Async

@Asyncpublic void cancelAudit(DefectForm defectForm) {Map<String,Object> params = new HashMap<>();params.put("defectId", defectForm.getDefectId()); //缺陷記錄IDparams.put("defectStatus", 3); //更新缺陷選項組審核拒絕params.put("reason", defectForm.getReason()); //拒絕理由defectRecordDao.updateByPrimaryKeySelective(params);
     //上面是業務處理,下面是發簡訊//審核拒絕傳送簡訊,簡訊發送給缺陷上報人,缺陷內容,審核拒絕理由Account account = accountDao.findAccountById(xxx);if(account != null && StringUtils.isNotBlank(account.getMobile())){String mobile = account.getMobile();String defectContent = defectForm.getDefectContent();String reason = defectForm.getReason();Map<String,String> templateData = new HashMap<>();templateData.put("defectContent", defectContent);templateData.put("reason", reason);smsService.sendSms(null, mobile, SmsConstant.DEFECT_REFUSRD_CODE, templateData,false);logger.debug("缺陷上報記錄審核拒絕,傳送簡訊給缺陷記錄上報人******");}}

3.前端邏輯:

/** * 審核拒絕,確定 * @returns */function makeRefuse(){var reason = $("#refuse_reason").val();if (reason==null || reason.trim()==""){AppUtils.showTooltip("請填寫拒絕理由!",false);return;}var curDefect = recordsJson[xxx];$.ajax({url: path + ‘/xxx/xxx/qqq/cancelAudit‘,type: ‘post‘,dataType: ‘json‘,data:curDefect,success: function(data){if(data=="ok"){AppUtils.showTooltip("審核拒絕成功!",true);$("#topForm").attr("action",path + ‘/xxx/xxx/xxx‘);$("#topForm").submit();}}});}

4.Controller層

@RequestMapping("/xxx/xxx/cancelAudit")@ResponseBodypublic String cancelAudit(DefectForm defectForm){defectRecordService.cancelAudit(defectForm);return "ok";}

  

經測試,可以非同步更新、傳送簡訊

但是,發現一個嚴重的問題:前台頁面點擊取消審核後頁面狀態偶爾能重新整理過來,偶爾還是之前的狀態,重新查詢一次後,頁面顯示正常

分析代碼:Controller層代碼寫的有問題,Controller層調用Service層(defectRecordService.cancelAudit(defectForm);),Service層cancelAudit(DefectForm defectForm)方法整個是@Async,

主線程會直接返回,而新啟的線程處理Service層的邏輯。這樣ajax返回前台,前台再去重新整理資料的時候,可能新啟線程Service的更新邏輯還沒處理完,這樣就導致了頁面重新整理狀態錯誤的問題

其實:我們期望的是,商務邏輯(更新操作)執行完成後再返回;整個商務邏輯(更新操作完成,返回)與發簡訊非同步

修改後的代碼:

 

1.Controller層

@RequestMapping("/xxx/xxx/cancelAudit")@ResponseBodypublic String cancelAudit(DefectForm defectForm){defectRecordService.cancelAudit(defectForm); //更新操作,成功後往下走,sendCancelAuditMsg會新啟一個線程處理,主線程繼續往下走,走到return "ok";返回 
//審核拒絕:業務操作完成後發簡訊defectRecordService.sendCancelAuditMsg(defectForm);return "ok";}

2.Service層

//這裡我們就不需要添加非同步註解了public void cancelAudit(DefectForm defectForm) {Map<String,Object> params = new HashMap<>();params.put("defectId", defectForm.getDefectId()); //缺陷記錄IDparams.put("defectStatus", 3); //更新缺陷選項組審核拒絕params.put("reason", defectForm.getReason()); //拒絕理由defectRecordDao.updateByPrimaryKeySelective(params);}

  

//把發簡訊的邏輯抽出來,單獨一個方法,使用非同步註解@Asyncpublic void sendCancelAuditMsg(DefectForm defectForm){//審核拒絕傳送簡訊,簡訊發送給缺陷上報人,缺陷內容,審核拒絕理由Account account = accountDao.findAccountById(defectForm.getCreatorUserid());if(account != null && StringUtils.isNotBlank(account.getMobile())){String mobile = account.getMobile();String defectContent = defectForm.getDefectContent();String reason = defectForm.getReason();Map<String,String> templateData = new HashMap<>();templateData.put("defectContent", defectContent);templateData.put("reason", reason);smsService.sendSms(null, mobile, SmsConstant.DEFECT_REFUSRD_CODE, templateData,false);logger.debug("缺陷上報記錄審核拒絕,傳送簡訊給缺陷記錄上報人******");}}

至此問題就解決了,寫部落格標註一下 

SpringBoot @Async 非同步處理商務邏輯和發簡訊邏輯

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.