0
  • 聊天消息
  • 系統(tǒng)消息
  • 評(píng)論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識(shí)你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示

SpringBoot循環(huán)依賴的癥狀和解決方案

Android編程精選 ? 來源:CSDN-熊貓Jay ? 2023-05-06 15:30 ? 次閱讀

什么是循環(huán)依賴?

循環(huán)依賴是指在Spring Boot 應(yīng)用程序中,兩個(gè)或多個(gè)類之間存在彼此依賴的情況,形成一個(gè)循環(huán)依賴鏈。

在這種情況下,當(dāng)一個(gè)類在初始化時(shí)需要另一個(gè)類的實(shí)例,而另一個(gè)類又需要第一個(gè)類的實(shí)例時(shí),就會(huì)出現(xiàn)循環(huán)依賴問題。這會(huì)導(dǎo)致應(yīng)用程序無法正確地初始化和運(yùn)行,因?yàn)镾pring Boot 無法處理這種循環(huán)依賴關(guān)系。

問題及癥狀

在2.6.0之前,Spring Boot會(huì)自動(dòng)處理循環(huán)依賴的問題。2.6.0及之后的版本會(huì)默認(rèn)檢查循環(huán)依賴,存在該問題則會(huì)報(bào)錯(cuò)。

ComponentA類注入ComponentB類,ComponentB類注入ComponentA類,就會(huì)發(fā)生循環(huán)依賴的問題。

ComponentA

importorg.springframework.stereotype.Service;
importjavax.annotation.Resource;

@Service
publicclassComponentA{

@Resource
privateComponentBcomponentB;

}

ComponentB

importorg.springframework.stereotype.Service;
importjavax.annotation.Resource;

@Service
publicclassComponentB{

@Resource
privateComponentAcomponentA;

}

錯(cuò)誤

現(xiàn)在,2.6.0 這個(gè)版本已經(jīng)默認(rèn)禁止 Bean 之間的循環(huán)引用, 則基于上面的代碼,會(huì)報(bào)錯(cuò):

***************************
APPLICATIONFAILEDTOSTART
***************************

Description:

Thedependenciesofsomeofthebeansintheapplicationcontextformacycle:

┌─────┐
|componentA
↑↓
|componentB
└─────┘


Action:

Relyinguponcircularreferencesisdiscouragedandtheyareprohibitedbydefault.Updateyourapplicationtoremovethedependencycyclebetweenbeans.Asalastresort,itmaybepossibletobreakthecycleautomaticallybysettingspring.main.allow-circular-referencestotrue.

解決方法

循環(huán)依賴是指兩個(gè)或更多的組件之間存在著互相依賴的關(guān)系。在Spring Boot應(yīng)用程序中,循環(huán)依賴通常是由以下幾種情況引起的:

構(gòu)造函數(shù)循環(huán)依賴: 兩個(gè)或更多的組件在它們的構(gòu)造函數(shù)中互相依賴。

屬性循環(huán)依賴: 兩個(gè)或更多的組件在它們的屬性中互相依賴。

方法循環(huán)依賴: 兩個(gè)或更多的組件在它們的方法中互相依賴。

Spring Boot提供了一些解決循環(huán)依賴的方法:

構(gòu)造函數(shù)注入: 在構(gòu)造函數(shù)中注入依賴項(xiàng),而不是在屬性中注入。

Setter注入: 使用setter方法注入依賴項(xiàng),而不是在構(gòu)造函數(shù)中注入。

延遲注入: 使用@Lazy注解延遲加載依賴項(xiàng)。

@Autowired注解的required屬性: 將required屬性設(shè)置為false,以避免出現(xiàn)循環(huán)依賴問題。

@DependsOn注解: 使用@DependsOn注解指定依賴項(xiàng)的加載順序,以避免出現(xiàn)循環(huán)依賴問題

構(gòu)造器注入的案例

假設(shè)有以下兩個(gè)類:

publicclassA{
privateBb;

publicA(){
//...
}

publicvoidsetB(Bb){
this.b=b;
}
}

publicclassB{
privateAa;

publicB(){
//...
}

publicvoidsetA(Aa){
this.a=a;
}
}

通過構(gòu)造函數(shù)注入可以避免循環(huán)依賴,改造后的代碼如下:

publicclassA{
privateBb;

publicA(Bb){
this.b=b;
}
}

publicclassB{
privateAa;

publicB(Aa){
this.a=a;
}
}

這樣,在創(chuàng)建 A 實(shí)例時(shí),只需要將 B 實(shí)例傳遞給 A 的構(gòu)造函數(shù)即可,不需要再通過 setter 方法將 B 實(shí)例注入到 A 中。同理,在創(chuàng)建 B 實(shí)例時(shí),只需要將 A 實(shí)例傳遞給 B 的構(gòu)造函數(shù)即可,不需要再通過 setter 方法將 A 實(shí)例注入到 B 中。這樣可以避免循環(huán)依賴。

延遲注入的案例

假設(shè)有如下情景:

類A依賴于類B,同時(shí)類B也依賴于類A。這樣就形成了循環(huán)依賴。

為了解決這個(gè)問題,可以使用@Lazy注解,將類A或類B中的其中一個(gè)延遲加載。

例如,我們可以在類A中使用@Lazy注解,將類A延遲加載,這樣在啟動(dòng)應(yīng)用程序時(shí),Spring容器不會(huì)立即加載類A,而是在需要使用類A的時(shí)候才會(huì)進(jìn)行加載。這樣就避免了循環(huán)依賴的問題。

示例代碼如下:

@Component
publicclassA{

privatefinalBb;

publicA(@LazyBb){
this.b=b;
}

//...
}

@Component
publicclassB{

privatefinalAa;

publicB(Aa){
this.a=a;
}

//...
}

在類A中,我們使用了@Lazy注解,將類B延遲加載。這樣在啟動(dòng)應(yīng)用程序時(shí),Spring容器不會(huì)立即加載類B,而是在需要使用類B的時(shí)候才會(huì)進(jìn)行加載。

這樣就避免了類A和類B之間的循環(huán)依賴問題。

接口隔離的案例

假設(shè)有兩個(gè)類A和B,它們之間存在循環(huán)依賴:

publicclassA{
privatefinalBb;
publicA(Bb){
this.b=b;
}
}

publicclassB{
privatefinalAa;
publicB(Aa){
this.a=a;
}
}

這時(shí)候,如果直接在Spring Boot中注入A和B,就會(huì)出現(xiàn)循環(huán)依賴的問題。為了解決這個(gè)問題,可以使用接口隔離。

首先,定義一個(gè)接口,包含A和B類中需要使用的方法:

publicinterfaceService{
voiddoSomething();
}

然后,在A和B類中分別注入Service接口:

publicclassA{
privatefinalServiceservice;
publicA(Serviceservice){
this.service=service;
}
}

publicclassB{
privatefinalServiceservice;
publicB(Serviceservice){
this.service=service;
}
}

最后,在Spring Boot中注入Service實(shí)現(xiàn)類:

@Service
publicclassServiceImplimplementsService{
privatefinalAa;
privatefinalBb;
publicServiceImpl(Aa,Bb){
this.a=a;
this.b=b;
}
@Override
publicvoiddoSomething(){
//...
}
}

通過這種方式,A和B類不再直接依賴于彼此,而是依賴于同一個(gè)接口。同時(shí),Spring Boot也能夠正確地注入A、B和ServiceImpl,避免了循環(huán)依賴的問題。

審核編輯:湯梓紅

聲明:本文內(nèi)容及配圖由入駐作者撰寫或者入駐合作網(wǎng)站授權(quán)轉(zhuǎn)載。文章觀點(diǎn)僅代表作者本人,不代表電子發(fā)燒友網(wǎng)立場(chǎng)。文章及其配圖僅供工程師學(xué)習(xí)之用,如有內(nèi)容侵權(quán)或者其他違規(guī)問題,請(qǐng)聯(lián)系本站處理。 舉報(bào)投訴
  • 接口
    +關(guān)注

    關(guān)注

    33

    文章

    8360

    瀏覽量

    150522
  • 函數(shù)
    +關(guān)注

    關(guān)注

    3

    文章

    4260

    瀏覽量

    62228
  • 應(yīng)用程序
    +關(guān)注

    關(guān)注

    37

    文章

    3223

    瀏覽量

    57503
  • spring
    +關(guān)注

    關(guān)注

    0

    文章

    335

    瀏覽量

    14277
  • Boot
    +關(guān)注

    關(guān)注

    0

    文章

    149

    瀏覽量

    35731
  • SpringBoot
    +關(guān)注

    關(guān)注

    0

    文章

    173

    瀏覽量

    153

原文標(biāo)題:SpringBoot 循環(huán)依賴的癥狀和解決方案

文章出處:【微信號(hào):AndroidPush,微信公眾號(hào):Android編程精選】歡迎添加關(guān)注!文章轉(zhuǎn)載請(qǐng)注明出處。

收藏 人收藏

    評(píng)論

    相關(guān)推薦

    2009最新LED路燈技術(shù)設(shè)計(jì)和解決方案

    2009年11月19-20日,OFweek光電新聞網(wǎng),LEDWeekly將舉辦“2009最新LED路燈技術(shù)設(shè)計(jì)和解決方案”系列在線研討會(huì)。歡迎朋友們參加, 詳細(xì)情況看這里~: http://webinar.ofweek.com/index.action?user.id=2 有興趣的朋友可以來參加! 
    發(fā)表于 11-08 23:57

    儀表放大器--常見的應(yīng)用問題和解決方案

    儀表放大器--常見的應(yīng)用問題和解決方案很完整的資料!
    發(fā)表于 12-15 09:53

    無線傳感器網(wǎng)絡(luò)的挑戰(zhàn)和解決方案

    無線傳感器網(wǎng)絡(luò)的挑戰(zhàn)和解決方案
    發(fā)表于 09-17 06:53

    EMI耦合類型和解決方案?

    、高性能和解決方案尺寸三個(gè)考慮因素通常相互沖突:只能優(yōu)先考慮一兩個(gè),而放棄第三個(gè),尤其當(dāng)設(shè)計(jì)期限臨近時(shí)。犧牲一些性能變得司空見慣;其實(shí)不應(yīng)該是這樣的。。
    發(fā)表于 10-22 14:10

    SpringBoot 學(xué)習(xí)筆記

    SpringBoot 學(xué)習(xí)筆記 【整合JWT】添加依賴創(chuàng)建工具類登錄獲取jwt使用jwtDemo源碼參考資料添加依賴pom.xml...com.auth0java-jwt3.12.0
    發(fā)表于 07-01 07:27

    springboot集成mqtt

    springboot集成mqtt,大綱一.數(shù)據(jù)入庫(kù)1.數(shù)據(jù)入庫(kù)解決方案二.開發(fā)實(shí)時(shí)訂閱發(fā)布展示頁(yè)面1.及時(shí)通訊技術(shù)2.技術(shù)整合
    發(fā)表于 07-16 07:53

    ADI鋰電池測(cè)試設(shè)備和解決方案

    ADI鋰電池測(cè)試設(shè)備和解決方案
    發(fā)表于 09-08 16:23 ?15次下載
    ADI鋰電池測(cè)試設(shè)備<b class='flag-5'>和解決方案</b>

    PFC+LLC的產(chǎn)品和解決方案分析

    PFC LLC英雄產(chǎn)品和解決方案
    的頭像 發(fā)表于 05-29 09:05 ?1w次閱讀
    PFC+LLC的產(chǎn)品<b class='flag-5'>和解決方案</b>分析

    Java:調(diào)用window的matlab遇到的問題和解決方案

    Java:調(diào)用window的matlab遇到的問題和解決方案
    的頭像 發(fā)表于 06-20 09:32 ?3263次閱讀
    Java:調(diào)用window的matlab遇到的問題<b class='flag-5'>和解決方案</b>

    無線傳感器網(wǎng)絡(luò)的挑戰(zhàn)和解決方案

    無線傳感器網(wǎng)絡(luò)的挑戰(zhàn)和解決方案
    發(fā)表于 03-19 04:28 ?4次下載
    無線傳感器網(wǎng)絡(luò)的挑戰(zhàn)<b class='flag-5'>和解決方案</b>

    AN-1429: 手機(jī)中耳機(jī)驅(qū)動(dòng)的設(shè)計(jì)考慮和解決方案

    AN-1429: 手機(jī)中耳機(jī)驅(qū)動(dòng)的設(shè)計(jì)考慮和解決方案
    發(fā)表于 03-20 13:06 ?7次下載
    AN-1429: 手機(jī)中耳機(jī)驅(qū)動(dòng)的設(shè)計(jì)考慮<b class='flag-5'>和解決方案</b>

    無線傳感器網(wǎng)絡(luò)的挑戰(zhàn)和解決方案

    無線傳感器網(wǎng)絡(luò)的挑戰(zhàn)和解決方案
    發(fā)表于 03-21 13:41 ?1次下載
    無線傳感器網(wǎng)絡(luò)的挑戰(zhàn)<b class='flag-5'>和解決方案</b>

    高可靠性組件和解決方案

    高可靠性組件和解決方案
    發(fā)表于 04-26 14:38 ?6次下載
    高可靠性組件<b class='flag-5'>和解決方案</b>

    關(guān)于Spring的循環(huán)依賴問題

      Spring 的循環(huán)依賴,源碼詳細(xì)分析 → 真的非要三級(jí)緩存嗎 中講到了循環(huán)依賴問題
    的頭像 發(fā)表于 06-14 17:21 ?1708次閱讀

    PCB金手指設(shè)計(jì)的常見問題和解決方案

    PCB金手指設(shè)計(jì)的常見問題和解決方案
    的頭像 發(fā)表于 12-25 10:09 ?1814次閱讀