SpringBoot3.x循環(huán)依賴(lài)問(wèn)題解決方案
問(wèn)題說(shuō)明
SpringBoot3.x版本已經(jīng)發(fā)布,從SpringBoot2.6.x后就做了很多的改變。
用過(guò)SpringBoot2.7.5~x版本的伙伴應(yīng)該會(huì)發(fā)現(xiàn),SpringBoot項(xiàng)目中如果存在循環(huán)依賴(lài)關(guān)系,則在啟動(dòng)項(xiàng)目的時(shí)候會(huì)出現(xiàn)異常錯(cuò)誤信息,提示內(nèi)容大致為:項(xiàng)目中存在循環(huán)依賴(lài),項(xiàng)目無(wú)法正常啟動(dòng)運(yùn)行。
自SpringBoot2.7.5~x版本以后至SpringBoot3.x都存在這個(gè)問(wèn)題,Spring已經(jīng)摒棄循環(huán)依賴(lài)的問(wèn)題,需要開(kāi)發(fā)人員自行解決,或在開(kāi)發(fā)過(guò)程中盡量避免循環(huán)依賴(lài)的出現(xiàn)。
對(duì)于舊版本項(xiàng)目升級(jí)的來(lái)說(shuō),這將會(huì)是一件很棘手的問(wèn)題,所有的存在循環(huán)依賴(lài)關(guān)系的代碼都需要重新調(diào)整,況且一不小心就會(huì)代碼崩潰無(wú)法運(yùn)行。
解決方案
第一種、開(kāi)啟循環(huán)依賴(lài)(不推薦)
Spring默認(rèn)已經(jīng)不在支持循環(huán)依賴(lài),在配置文件中重新開(kāi)啟循環(huán)依賴(lài)支持
spring:
main:
allow-circular-references:true #允許循環(huán)引用第二種、懶加載
@Lazy:配合使用該注解可以解決循環(huán)依賴(lài)問(wèn)題(在需要注入Bean的地方加上該注解)
@Lazy // 使用懶加載 @Autowired private OneService oneService;
第三種、控制反轉(zhuǎn)
@Service
@RequiredArgsConstructor // 該注解的使用在下面會(huì)有介紹和說(shuō)明
public class OneServiceImpl implements OneService {
private final ConfigurableListableBeanFactory beanFactory;
//代替循環(huán)依賴(lài)
public TwoService getTwoService(){
return beanFactory.getBean(TwoService.class);
}
}使用
getTwoService()直接從bean工廠里面去拿對(duì)應(yīng)的Bean來(lái)使用
@Service
@RequiredArgsConstructor // 該注解的使用在下面會(huì)有介紹和說(shuō)明
public class TwoServiceImpl implements TwoService {
private final ConfigurableListableBeanFactory beanFactory;
//代替循環(huán)依賴(lài)
public OneService getOneService(){
return beanFactory.getBean(OneService.class);
}
}以上代碼中,OneService依賴(lài)于TwoService,而TwoService也依賴(lài)于OneService,從而產(chǎn)生循環(huán)依賴(lài)
解決:每次使用的時(shí)候就去Bean工廠里去獲取,這樣就不存在循環(huán)依賴(lài)了
@RequiredArgsConstructor使用說(shuō)明
@RequiredArgsConstructor:該注解是由Lombok提供,可以解決掉大量重復(fù)的@Autowired代碼
注意:使用@RequiredArgsConstructor時(shí),需要使用final關(guān)鍵字
寫(xiě)在類(lèi)上可以代替@Autowired注解,需要注意的是在注入時(shí)需要用final定義,或者使用@notnull注解
@RestController
@RequiredArgsConstructor // 代替@Autowired注解
@RequestMapping("/api/v1/one")
public class OneController{
private final OneService oneService; // 需要final關(guān)鍵字
private final TwoService twoService; // 需要final關(guān)鍵字
@GetMapping("{id}")
public ResultVo<String> getDetails(@PathVariable("id") Long id){
return ResultVo.ok(oneService.getDetailsById(id));
}
}注意點(diǎn):
1、必須聲明的變量為final。
2、根據(jù)構(gòu)造器注入的,相當(dāng)于容器調(diào)用帶有一組帶有參數(shù)的類(lèi)構(gòu)造函數(shù)時(shí),基于構(gòu)造函數(shù)的 DI 就完成了,其中每個(gè)參數(shù)代表一個(gè)對(duì)其他類(lèi)的依賴(lài)。基于構(gòu)造方法為屬性賦值,容器通過(guò)調(diào)用類(lèi)的構(gòu)造方法將其進(jìn)行依賴(lài)注入。
3、當(dāng)需要注入Bean的時(shí)候可以直接在類(lèi)名稱(chēng)上使用@RequiredArgsConstructor,從而代替了大量的@Autowrited注解。
到此這篇關(guān)于SpringBoot3.x循環(huán)依賴(lài)的文章就介紹到這了,更多相關(guān)SpringBoot循環(huán)依賴(lài)內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Spring?AOP通知類(lèi)型與實(shí)戰(zhàn)示例講解
Spring?AOP提供了五種通知類(lèi)型:@Before、@After、@AfterReturning、@AfterThrowing和@Around,每種通知類(lèi)型都有其特定的使用場(chǎng)景和實(shí)現(xiàn)方式,通過(guò)合理使用這些通知類(lèi)型,可以實(shí)現(xiàn)各種橫切關(guān)注點(diǎn)的模塊化和解耦,感興趣的朋友跟隨小編一起看看吧2024-11-11
springboot一個(gè)自定義注解如何搞定多線程事務(wù)
文章介紹了Spring?Boot中使用`@Async`注解進(jìn)行聲明式多線程編程的方法,以及如何通過(guò)自定義注解和AOP實(shí)現(xiàn)多線程事務(wù)控制,同時(shí),還解釋了`CountDownLatch`的使用場(chǎng)景及其工作原理2024-12-12
使用IDEA直接連接MySQL數(shù)據(jù)庫(kù)的方法
這篇文章主要介紹了如何使用IDEA直接連接MySQL數(shù)據(jù)庫(kù),首先需要新建一個(gè)空項(xiàng)目,第一次連接 需要先下載驅(qū)動(dòng),文中給大家介紹的非常詳細(xì),感興趣的朋友跟隨小編一起看看吧2024-04-04
SpringBoot全局異常捕獲參數(shù)以及參數(shù)異常的解決方案
這篇文章主要介紹了SpringBoot全局異常捕獲參數(shù)以及參數(shù)異常的解決方案,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2025-05-05
java8新特性-Stream入門(mén)學(xué)習(xí)心得
這篇文章主要介紹了java8新特性-Stream入門(mén)學(xué)習(xí)心得,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-03-03
Java SpringMVC 異常處理SimpleMappingExceptionResolver類(lèi)詳解
這篇文章主要介紹了SpringMVC 異常處理SimpleMappingExceptionResolver類(lèi)詳解,本篇文章通過(guò)簡(jiǎn)要的案例,講解了該項(xiàng)技術(shù)的了解與使用,以下就是詳細(xì)內(nèi)容,需要的朋友可以參考下2021-09-09

