Spring事務(wù)監(jiān)聽機(jī)制—使用@TransactionalEventListener處理數(shù)據(jù)庫事務(wù)提交成功后再執(zhí)行操作
- 為什么使用
在項(xiàng)目中,往往需要執(zhí)行數(shù)據(jù)庫操作后,發(fā)送消息或事件來異步調(diào)** * 用其他組件執(zhí)行相應(yīng)的操作,例如:
用戶注冊后發(fā)送激活碼;
配置修改后發(fā)送更新事件等。
但是,數(shù)據(jù)庫的操作如果還未完成,此時(shí)異步調(diào)用的方法查詢數(shù)據(jù)庫發(fā)現(xiàn)沒有數(shù)據(jù),這就會出現(xiàn)問題。- 為了解決上述問題,Spring為我們提供了兩種方式:
(1) @TransactionalEventListener注解
(2) 事務(wù)同步管理器TransactionSynchronizationManager
以便我們可以在事務(wù)提交后再觸發(fā)某一事件。
1、定義被監(jiān)聽的元素
/**
* 定義個(gè)被監(jiān)聽的元素
* @author jarfly
*/
@Data
@AllArgsConstructor
public class UserEvent {
/**
* 用戶信息
*/
private final User user;
}
2、定義監(jiān)聽事件
@Component
public class UserEventListener {
@Async
@TransactionalEventListener(classes = SaveUserEvent.class,phase = TransactionPhase.AFTER_COMMIT )
void onSaveUserEvent(SaveUserEvent event) {
Integer id = event.getEventData();
User u = userDao.getUserById(id);
String phone = u.getPhoneNumber();
MessageUtils.sendMessage(phone);
}
}
3、發(fā)布事件
@Service
public class UserServiceImpl implements UseService {
@Autowired
private ApplicationContext applicationContext;
@Transaction
void saveUser(User u) {
//保存用戶信息
userDao.save(u);
//觸發(fā)保存用戶事件
applicationContext.publishEvent(new SaveUserEvent(u.getId()));
}
}
更詳細(xì)的介紹
https://blog.csdn.net/qq_41378597/article/details/105748703