如何解決SpringBoot2.6及之后版本取消了循環(huán)依賴的支持問題
1、問題
循環(huán)依賴指的是兩個(gè)或者多個(gè)bean之間相互依賴,形成一個(gè)閉環(huán)。直接表現(xiàn)為兩個(gè)service層互相調(diào)用對方。
此時(shí)會(huì)遇到以下問題:
2、報(bào)錯(cuò)
當(dāng)啟動(dòng)項(xiàng)目時(shí),可能出現(xiàn)程序不能啟動(dòng)的情況,查看調(diào)試日志,會(huì)提示:
The dependencies of some of the beans in the application context form a cycle...
如下圖所示:
根據(jù)上述代碼片段,應(yīng)用程序存在以下循環(huán)依賴:
1. adminBorrowInfoController 依賴 borrowInfoServiceImpl
2. borrowInfoServiceImpl 依賴 lendServiceImpl
3. lendServiceImpl 依賴 lendItemServiceImpl
4. lendItemServiceImpl 又反過來依賴 lendServiceImpl
這樣就形成了一個(gè)循環(huán)依賴的場景。
原因是SpringBoot 從 2.6.0 開始默認(rèn)不允許出現(xiàn) Bean 循環(huán)引用。而且這個(gè)是在Bean 定義上也就是類上就不允許出現(xiàn)循環(huán)引用。
3、解決方案
第1種、在全局配置文件設(shè)置允許循環(huán)引用存在
升級到Spring Boot 2.7及以上版本,可以通過spring.main.allow-circular-references=true配置屬性明確開啟循環(huán)依賴支持。
但我用的2.6.11也可以哦,2.6以上的可以試試。
spring: main: allow-circular-references:true
第2種、在SpringApplicationBuilder 添加設(shè)置允許循環(huán)引用
使用SpringApplicationBuilder來啟動(dòng)Spring Boot應(yīng)用,并通過allowCircularReferences(true)方法開啟了循環(huán)依賴支持。
public static void main(String[] args) { new SpringApplicationBuilder(DemoApplication.class).allowCircularReferences(true).run(args); }
第N種、還有很多種供大家了解使用
1. 構(gòu)造器注入
- 在類中定義構(gòu)造器,添加需要依賴的類作為參數(shù)
- 使用@Autowired注解構(gòu)造器
- Spring會(huì)先實(shí)例化依賴類,然后通過構(gòu)造器注入
2. @Lazy
- 在導(dǎo)致循環(huán)依賴的Bean上添加@Lazy注解
- Spring會(huì)延遲初始化這些Bean,先完成非Lazy的Bean初始化
- 然后再通過setter注入完成Lazy Bean的初始化
3. ObjectFactory
- 定義ObjectFactory屬性,類型為對應(yīng)類的ObjectFactory
- Spring會(huì)代理注入ObjectFactory,獲取對象時(shí)才初始化目標(biāo)Bean
4. 服務(wù)定位器
- 定義一個(gè)統(tǒng)一的服務(wù)定位器類
- Bean直接從定位器獲取依賴對象,而不是注入依賴
5. 合并類
- 將互相依賴的類合并為一個(gè)類,避免相互依賴
6. 事件回調(diào)
- 使用事件或者回調(diào)方式實(shí)現(xiàn)解耦
- 一個(gè)類通過事件通知另一個(gè)類執(zhí)行操作,而不是直接調(diào)用
7. 接口編程
- 類依賴接口,不依賴具體實(shí)現(xiàn)
- 具體實(shí)現(xiàn)通過setter注入接口
以上是一些主要的具體實(shí)現(xiàn)步驟,可以根據(jù)實(shí)際情況選擇適合的方案。
總體上,出現(xiàn)循環(huán)依賴通常意味著系統(tǒng)設(shè)計(jì)需要優(yōu)化和解耦,需要重新梳理服務(wù)的職責(zé)和依賴關(guān)系,減少不必要的互相依賴,以提高內(nèi)聚性和可維護(hù)性。
這些僅為個(gè)人經(jīng)驗(yàn),希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。
- springboot循環(huán)依賴問題案例代碼及解決辦法
- SpringBoot3.x循環(huán)依賴問題解決方案
- springboot配置允許循環(huán)依賴問題
- SpringBoot啟動(dòng)報(bào)錯(cuò)屬性循環(huán)依賴報(bào)錯(cuò)問題的解決
- Springboot詳細(xì)講解循環(huán)依賴
- SpringBoot2.6.x默認(rèn)禁用循環(huán)依賴后的問題解決
- springboot bean循環(huán)依賴實(shí)現(xiàn)以及源碼分析
- 基于SpringBoot構(gòu)造器注入循環(huán)依賴及解決方式
- Springboot循環(huán)依賴的原因及解決
相關(guān)文章
java 域?qū)ο蠊蚕頂?shù)據(jù)的實(shí)現(xiàn)
本文主要介紹了java 域?qū)ο蠊蚕頂?shù)據(jù)的實(shí)現(xiàn),文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2023-03-03java運(yùn)行時(shí)數(shù)據(jù)區(qū)域和類結(jié)構(gòu)詳解
這篇文章主要介紹了java運(yùn)行時(shí)數(shù)據(jù)區(qū)域和類結(jié)構(gòu),具有很好的參考價(jià)值,希望對大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2021-07-07SpringBoot+log4j2.xml使用application.yml屬性值問題
這篇文章主要介紹了SpringBoot+log4j2.xml使用application.yml屬性值問題,具有很好的參考價(jià)值,希望對大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-12-12Post請求參數(shù)是數(shù)組或者List時(shí)的請求處理方式
這篇文章主要介紹了Post請求參數(shù)是數(shù)組或者List時(shí)的請求處理方式,具有很好的參考價(jià)值,希望對大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2024-05-05Java 調(diào)用Restful API接口的幾種方式(HTTPS)
這篇文章主要介紹了Java 調(diào)用Restful API接口的幾種方式(HTTPS),小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧2018-02-02java Spring 5 新特性函數(shù)式Web框架詳細(xì)介紹
正如昨天Juergen博客中所提到的,Spring 5.0的第二個(gè)里程碑是引入了一個(gè)新的函數(shù)式web框架。在這篇文章中,我們將給出關(guān)于這個(gè)框架的更多信息,,需要的朋友可以參考下2016-12-12Java ByteBuffer網(wǎng)絡(luò)編程用法實(shí)例解析
這篇文章主要介紹了Java ByteBuffer網(wǎng)絡(luò)編程用法實(shí)例解析,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2020-10-10FileUtils擴(kuò)展readURLtoString讀取url內(nèi)容
這篇文章主要介紹了FileUtils擴(kuò)展readURLtoString使用其支持讀取URL內(nèi)容為String,支持帶POST傳大量參數(shù),大家參考使用吧2014-01-01IntelliJ IDEA優(yōu)化配置的實(shí)現(xiàn)
這篇文章主要介紹了IntelliJ IDEA優(yōu)化配置的實(shí)現(xiàn),文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2020-07-07