欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

Springboot循環(huán)依賴的原因及解決

 更新時(shí)間:2025年05月07日 11:05:47   作者:帝錦_li  
本文主要介紹了Spring Boot中的循環(huán)依賴問題,包括循環(huán)依賴的定義、產(chǎn)生原因以及解決方法,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧

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

循環(huán)依賴(Circular Dependency) 是指兩個(gè)或多個(gè) Bean 相互直接或間接依賴,導(dǎo)致容器無法正常初始化這些 Bean。

@Service
public class ServiceA {
    @Autowired
    private ServiceB serviceB; // ServiceA 依賴 ServiceB
}

@Service
public class ServiceB {
    @Autowired
    private ServiceA serviceA; // ServiceB 依賴 ServiceA
}

Spring Boot 基于 Spring 框架,其循環(huán)依賴的處理機(jī)制與 Spring 一致,但在 Spring Boot 2.6+ 版本中默認(rèn)禁止了循環(huán)依賴(通過 spring.main.allow-circular-references=false)。 

產(chǎn)生循環(huán)依賴的原因

1.構(gòu)造函數(shù)注入循環(huán)依賴

@Service
public class ServiceA {
    private final ServiceB serviceB;
    public ServiceA(ServiceB serviceB) { // 構(gòu)造函數(shù)注入
        this.serviceB = serviceB;
    }
}

@Service
public class ServiceB {
    private final ServiceA serviceA;
    public ServiceB(ServiceA serviceA) { // 構(gòu)造函數(shù)注入
        this.serviceA = serviceA;
    }
}
  • 直接報(bào)錯(cuò):構(gòu)造函數(shù)注入的循環(huán)依賴無法解決,容器啟動(dòng)時(shí)拋出 BeanCurrentlyInCreationException

2.Setter/Field 注入循環(huán)依賴

在spring中使用@Autowired注解標(biāo)簽進(jìn)行自動(dòng)注入,如果不加以處理,會(huì)出現(xiàn)循環(huán)依賴問題 。

怎么解決循環(huán)依賴

在Springboot2.5以前可以通過三級(jí)緩存解決單例 Bean 的循環(huán)依賴問題。

緩存名稱職責(zé)
singletonObjects存放完全初始化好的 Bean(一級(jí)緩存)
earlySingletonObjects存放提前暴露的早期 Bean(二級(jí)緩存)
singletonFactories存放 Bean 的工廠對(duì)象(三級(jí)緩存)

以最初的ServiceA與ServiceB為例,

  • 創(chuàng)建 ServiceA,通過工廠將其半成品引用存入三級(jí)緩存。

  • ServiceA 注入 ServiceB,觸發(fā) ServiceB 的創(chuàng)建。

  • 創(chuàng)建 ServiceB,同樣將其半成品引用存入三級(jí)緩存。

  • ServiceB 注入 ServiceA 時(shí),從三級(jí)緩存中獲取 ServiceA 的早期引用,完成 ServiceB 的初始化。

  • ServiceB 初始化完成后,ServiceA 完成依賴注入,最終初始化。

 出現(xiàn)循環(huán)依賴之后的幾個(gè)解決思路:

1.避免循環(huán)依賴(推薦)

  • 重構(gòu)代碼:將公共邏輯抽離到第三個(gè) Bean 中。

  • 使用接口或抽象類:通過面向接口編程解耦具體實(shí)現(xiàn)。

2. 允許循環(huán)依賴(臨時(shí)方案)

在 application.properties 中顯式允許循環(huán)依賴:

# Spring Boot 2.6+ 需要手動(dòng)開啟
spring.main.allow-circular-references=true

這種只適用于Springboot版本在2.6以上的循環(huán)依賴被禁止的情形。 

3. 使用 @Lazy 延遲加載

在其中一個(gè)依賴上添加 @Lazy,延遲注入 Bean 的初始化:

@Service
public class ServiceA {
    @Lazy
    @Autowired
    private ServiceB serviceB; // 延遲初始化 ServiceB
}

4. 調(diào)整注入方式

 優(yōu)先使用 Setter/Field 注入:避免構(gòu)造函數(shù)注入導(dǎo)致的不可解循環(huán)依賴。

@Service
public class ServiceA {
    private ServiceB serviceB;
    
    @Autowired
    public void setServiceB(ServiceB serviceB) { // Setter 注入
        this.serviceB = serviceB;
    }
}

 使用setter注入

循環(huán)依賴的局限性

  • 構(gòu)造函數(shù)注入無法解決循環(huán)依賴:Spring 容器在創(chuàng)建 Bean 時(shí)需先完成構(gòu)造函數(shù)調(diào)用,此時(shí)依賴的 Bean 尚未初始化。

  • 原型(Prototype)作用域的 Bean:Spring 不管理原型 Bean 的完整生命周期,無法解決其循環(huán)依賴。

  • AOP 代理問題:如果 Bean 被 AOP 代理(如 @Async@Transactional),可能導(dǎo)致循環(huán)依賴解決失敗。

總結(jié)

Spring Boot 的循環(huán)依賴本質(zhì)是 Spring 框架的機(jī)制問題,解決核心在于:

  • 理解三級(jí)緩存的工作原理。

  • 優(yōu)先通過代碼設(shè)計(jì)避免循環(huán)依賴。

  • 必要時(shí)合理使用 @Lazy 或調(diào)整注入方式。

 盡可能在設(shè)計(jì)之初就避免循環(huán)依賴

到此這篇關(guān)于Springboot循環(huán)依賴的原因及解決的文章就介紹到這了,更多相關(guān)Springboot循環(huán)依賴內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Spring解密之XML解析與Bean注冊(cè)示例詳解

    Spring解密之XML解析與Bean注冊(cè)示例詳解

    這篇文章主要給大家介紹了關(guān)于Spring解密之XML解析與Bean注冊(cè)的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面小編來一起學(xué)習(xí)學(xué)習(xí)吧。
    2018-01-01
  • JAVA JVM面試題總結(jié)

    JAVA JVM面試題總結(jié)

    JVM 可以屏蔽與具體操作系統(tǒng)平臺(tái)相關(guān)的信息,使 Java 程序只需生成在 Java 虛擬機(jī)上運(yùn)行的目標(biāo)代碼,就可以在不同的平臺(tái)上運(yùn)行。這篇文章主要介紹了JAVA JVM面試題總結(jié),大家可以參考一下
    2021-08-08
  • Java程序包裝成桌面應(yīng)用程序方式

    Java程序包裝成桌面應(yīng)用程序方式

    這篇文章主要介紹了Java程序包裝成桌面應(yīng)用程序方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2023-01-01
  • SpringSecurity自定義登錄成功處理

    SpringSecurity自定義登錄成功處理

    這篇文章主要為大家詳細(xì)介紹了SpringSecurity自定義登錄成功處理,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2022-09-09
  • Java CompletableFuture的使用詳解

    Java CompletableFuture的使用詳解

    這篇文章主要介紹了Java CompletableFuture的使用詳解,幫助大家更好的理解和學(xué)習(xí)使用Java,感興趣的朋友可以了解下
    2021-03-03
  • Java多線程之CAS算法實(shí)現(xiàn)線程安全

    Java多線程之CAS算法實(shí)現(xiàn)線程安全

    這篇文章主要介紹了java中如何通過CAS算法實(shí)現(xiàn)線程安全,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,下面小編和大家一起來學(xué)習(xí)一下吧
    2019-05-05
  • Java 數(shù)組(Array)存儲(chǔ)數(shù)據(jù)的“排排坐”(最新推薦)

    Java 數(shù)組(Array)存儲(chǔ)數(shù)據(jù)的“排排坐”(最新推薦)

    這篇文章主要介紹了Java 數(shù)組(Array)存儲(chǔ)數(shù)據(jù)的“排排坐”(最新推薦),本文通過實(shí)例代碼給大家介紹的非常詳細(xì),感興趣的朋友一起看看吧
    2025-05-05
  • Java持久化框架Hibernate與Mybatis優(yōu)劣及選擇詳解

    Java持久化框架Hibernate與Mybatis優(yōu)劣及選擇詳解

    這篇文章主要介紹了Java持久化框架Hibernate與Mybatis優(yōu)劣及選擇詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-05-05
  • idea中使用git插件回滾代碼的流程步驟

    idea中使用git插件回滾代碼的流程步驟

    使用idea開發(fā)java代碼時(shí),如果想回滾git提交的代碼, 需要操作三步,本篇步驟操作前,前提是你的電腦已經(jīng)安裝了git插件,并且你的idea也集成了git插件,下面是詳細(xì)步驟,需要的朋友可以參考下
    2025-04-04
  • springboot升級(jí)到j(luò)dk21最新教程(2023年)

    springboot升級(jí)到j(luò)dk21最新教程(2023年)

    你還在使用jdk8?快來看看最新出爐的SpringBoot+jdk21如何使用,下面這篇文章主要給大家介紹了關(guān)于springboot升級(jí)到j(luò)dk21的相關(guān)資料,文中通過代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2023-10-10

最新評(píng)論