我們使用的 mongoD B4.0副本集 ,正常是支持事務操作的,但是開發運維兩年
,某一次發生例外但是事務并沒有回滾,導致資料對不上,意識到需要驗證下事務是否還生效,單元測驗驗證 @Transactional 并未生效,查找原因,一開始以為是mongo的問題,但是兩年前開始使用mongo就驗證過了事務,一開始網路上找的答案都是如何配置,并未有效果,后來創建了個簡單的專案,只引入相同版本spring data mongo 依賴事務生效,同時 @Async 執行緒異步 也生效,
同時對比了兩個專案的輸出日志 發現 測驗 專案單元測驗執行 會開啟Transactional session,最后commit提交到資料庫中 ,此階段在Navicat客戶端是查不到那條資料的,因為沒有commit,但是 失效的專案 debug斷住查看已經保存到資料庫里了,不會回滾,

后來 感覺問題有三種可能
- 依賴沖突
- 改動過spring data mongo的原始碼 ,因為當時那個版本aggregate關聯原始碼會報錯,還有 保存string到資料庫里是 ObjectId型別,不方便關聯
- bean沖突
找問題 重新拉取了一樣專案, 刪減 依賴 改動原始碼 發現不是 這兩個問題
然后只能一點一點洗掉配置的類 依賴 以及相關代碼 最后發現 是shiro的問題
(此階段 用了 兩天)
就上網搜索 springboot + shiro 導致事物不生效的問題,后來找到幾個博客,找到了答案
解答文章鏈接
總結下來就是:
由于ShiroFilterFactoryBean實作了FactoryBean介面,所以它會提前被初始化,又因為SecurityManager,SecurityManager依賴于Realm實作類、Realm實作類又依賴于UserService,所以引發所有相關的bean提前初始化,
ShiroFilterFactoryBean -> SecurityManager -> Realm實作類 -> UserService
但是此時還只是ApplicationContext中registerBeanPostProcessors注冊BeanPostProcessor處理器的階段,此時AnnotationAwareAspectJAutoProxyCreator還沒有注冊到BeanFactory中,UserService無法享受到事務處理!
就是說在realm中注入的所有service都會提前加載,連帶注入的service中,如果還有其他service注入也會提前加載,無法享受事務處理,
解決方案:
1.在realm中注入service時,加上@lazy注解
2.不在realm注入service
@Async 注解也需要 懶加載 ,要不可能會失效
希望可以幫助到你!
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/275741.html
標籤:其他
