a commponent required a bean of type XXXXXX that could not be found-2022新專案

一隻愛閱讀的程式設計師發表於2022-05-11

一、問題由來

  目前剛入職一家新公司不久,公司的新專案採用DDD驅動領域設計來進行開發,架構這一塊使用的是阿里巴巴開源的最新框架COLA4.0的架構。

主要是這個框架裡面的分層設計。主要分為四層:adapter適配層類似於以前的Controller層;app層類似於以前的Service層;domain層是領域層;還有

一個infrastructure層表示基礎設施服務層,提供基礎服務,比如資料庫服務。專案還是進行設計階段,自己主要負責開發這一塊。由於大家都是剛開始

接觸DDD這個新知識,因此還有很多東西都需要學習。由於我們負責的這個專案屬於通用域,而且人手也不是太多,因此很多東西都需要親力親為。

比如說搭建專案框架,基礎架構採用cola4.0,裡面具體使用什麼版本的SpringBoot,SpringCloud,Redis,Postgresql等等,都得我們自己來定。自己

也沒閒著,立馬去學習Cola4.0這個框架,由於這種設計理念很是新穎,因此在網上可供參考學習的資料很少。不像什麼SpringBoot,springCloud之類的

課程,一搜就一堆的答案。Cola4.0的框架的大致架構如圖所示:

詳細的錯誤資訊如下:

a component required a bean of type xxxxxx that could not be found
Action
Consider defining a bean of type xxxxxx in your configuration


二、問題分析

  從錯誤資訊來看,大致意思就是元件找不到型別為xxxxxx的bean,可以考慮在配置中定義一個bean。自己根據實際情況來判斷報錯的型別是一個介面,

這個介面有具體的實現類,實現類中使用的註解為@Component.這個介面有在其他地方被使用,啟動專案時由於這個類沒有被載入到,因此報這個錯。能

確定一點就是介面的實現類沒有被載入到,可是為什麼沒有被載入到呢?框架是我們按照cola4.0的架構自己來搭建的,它裡面就是一些簡單的骨架,沒有

具體封裝一些程式碼之類的,我們用的話也只會考慮使用它的架構。這就很讓人疑惑,使用原作者的框架就可以正常執行,怎麼自己來搭建就不行了呢?


三、解決方案

      拿到這個錯誤資訊,自己立馬開始使用搜尋引擎。由於這個專案比較特殊,啟動類是單獨為一個start專案,主要作用就是用來啟動

專案,不做其他任何事情。

嘗試方案一:

推測介面實現類中沒有新增對應的註解,所以不能被掃描到。

自己經過檢查,發現所有的介面實現類都新增了@Component註解。會不會有這種可能,這個註解不生效?

於是自己換成@Service註解,重新啟動專案,發現問題任然未解決。

參考文章 https://blog.csdn.net/qq_39691492/article/details/118085232

 

嘗試方案二:

推測導致這個錯誤的原因可能是由於介面的實現類沒有被掃描到,沒有正確載入到spring容器中,最終出現問題。

使用@ComponentScan包掃描註解,把介面實現類的包路徑放進去,然後重新啟動專案。結果為解決。

參考文章 https://blog.csdn.net/suxiexingchen/article/details/84984349

 

嘗試方案三:

推測可能是包結構不對導致來載入錯誤。這到是有可能,然後自己仔細檢查了專案的包結構,排除此問題,包結構

沒有問題,還是沒有解決。

https://blog.csdn.net/Julycaka/article/details/80622754

 

這時候自己就開始分析,說先確定一點介面的實現類沒有被載入到spring容器中,為什麼會沒有被載入到呢?然後自己

倒回去看看cola4.0的例子,檢視模組之間的相互引用關係,這時發現問題了。demo例子中app層直接引用了infrastructure,

我們自己搭建的框架中沒有做這個引用,這就導致infrastructure層中的程式碼沒有被正確掃描到,繼而不能被載入到spring容器中。

自己立馬去app層中新增該模組,然後重新啟動專案,發現啟動成功,問題解決。

 

總結:使用maven進行多模組開發的時候,需要確保所有的模組中的包路徑都能被掃描到,否則就會導致類載入不了的問題。

不管是直接引用還是間接引用,只有所有的模組都和啟動類關聯起來後,專案才能夠正常啟動。我們的專案中引用關係如下:

start層 引用 adapter層;

adapter層 引用 app層; 

app層 引用 domain層;app層 引用 infrastructure層;

infrastructure層 引用 domain層; 

common層被除start層外的所有模組引用;

這樣雖然專案啟動層start中只有一個啟動類,通過這種直接的或者是間接的引用關係就可以載入所有的bean物件。

相關文章