使用Gradle構建多模塊SpringBoot項目
本項目使用Gradle構建SpringBoot項目,將不同的業務進行不同的模塊划分(不做微服務與分布式架構);
- 編輯器:Intellij IDEA
- 構建工具:Gradle3.5
- SpringBoot版本:1.5.8
- 版本管理:GitHub
- 個人GitHub地址:https://github.com/fanlongfei0212
- 項目Clone地址:https://github.com/fanlongfei0212/demo.git
項目構建
-
首先創建一個項目,我們使用IDEA構建一個Gradle Java項目,作為項目的最外層,只做為整個項目的容器,所以最外層項目只構建為普通的Gradle Java項目即可;
-
填寫GroupId與ArtifactId;
一般正式項目的GroupId為com.*開頭,因為此項目為個人項目,所以使用pers.*開頭,具體規則大家可以參考命名規范,ArtifactId為項目名稱;
-
點擊Next,進入Gradle配置頁面;
選擇Use local gradle distribution,配置自己本地的Gradle地址;
點擊Next,Project name自動為ArtifactId,Project location為IDEA默認(或你上一次設置)的WorkSpace,分配WorkSpace;
點擊Finish,完成Gradle Java項目的創建



-
項目已經創建好了,我們開始創建各個模塊,在不同項目中,模塊划分的方式也會不同,具體的模塊划分可以按照實際項目的需求進行划分;
在此Demo中,將模塊划分為:
全局工具模塊:tools-common(項目中所有模塊的全局工具類,基礎模塊依賴此模塊,下面會講到基礎模塊)
視圖模塊:views-demo(項目中的視圖模塊,比如:APP所需接口、管理后台所需接口,需要進行數據展示的模塊,都會被此模塊依賴)
業務模塊:service-demo1(將項目中不同業務進行模塊化的區分,一般在項目中,業務模塊是最多的,而且在某個業務模塊中需要其他業務模塊作為支撐的可以進行Gradle依賴,但要避免循環依賴)
基礎模塊:basic-base(項目中所有業務模塊的支撐,此模塊中提供的基礎服務是所有業務模塊中都要用到的,所有業務模塊都要依賴此模塊,此模塊依賴全局工具模塊,這樣,所有的模塊都相當於間接依賴了全局工具模塊) -
1.創建全局工具模塊:
右鍵項目,點擊 New -> Moduel,選擇Spring Initializr,點擊Next

-
2.配置模塊:
設置Group,最好與項目的GroupId保持一致;
設置Artifact,模塊名稱;
設置Type,我們使用的是Gradle進行項目構建,所以選擇Gradle Project;
點擊Next
-
3.配置SpringBoot,也可以不再此處進行配置,直接在模塊中的Gradle文件中添加依賴也可以起到同樣的作用,最后在同一說明處會有講解,我們先在此處進行配置:
Core:DevTools(項目中一些開發工具,比如熱部署等)、Lombok(消除冗長的Java代碼,比如get、set、構造函數等,可以直接使用注解);
Web:Web(Spring的一些Web配置);
SQL:JPA、MySQL(我使用的是MySQL,大家可以根據實際情況進行數據庫選擇);
Ops:Actuator(項目監控);
點擊Next,會發現Module name為Artifact,和創建項目時一樣,點擊Finish -
注:大家可以根據自己的項目情況進行SpringBoot的配置,配置好之后再窗體中的右邊Selected Dependencies可以查看已選的SpringBoot配置


-
4.設置Use local gradle distribution配置Gradle,選擇本地的Gradle地址,點擊OK,完成創建模塊;

-
5.進行Gradle配置,大家可以看到,右邊的的Gradle視圖也多了一個tools-common的模塊,但是有一個問題,他和項目模塊是平級的,在Gradle項目中,根項目應該在最外層,其他模塊都應包含在根項目中,我們設置最外層settings.gradle文件,把模塊include到最外層的項目中,然后刷新Gradle
大家會發現有的時候可能會出現兩個根,其實只有一個,在Mac下初步判定是IDEA的兼容或顯示問題,大家刪除最下面的那個就可以了(選中第二個根,點擊Gradle視圖上的‘-’即可),正常刪除的時候Gradle會出現刪除提示,但是刪除錯誤顯示的時候你會發現,沒有提示,這是正常的,因為具有真實存在的根

-
6.所有的模塊進行統一步驟的創建
-
7.進行所有模塊的Gradle配置,配置各個模塊之間的依賴,將根Gradle的sourceCompatibility設置為1.8(我的JDK使用的是1.8),然后刷新Gradle,刪除多余的根(如果出現的話)



-
8.整理項目中文件
將無用的文件進行刪除;
刪除所有模塊中的gradlew文件
刪除所有模塊中的gradlew.bat文件
刪除所有模塊中的gradle文件夾
刪除所有模塊中的.gitignore文件,在項目最外層配置.gitignore文件,做為整個項目的git提交忽略配置

-
9.配置SpringBoot的application.properties文件:
將所有模塊application.properties進行重新命名修改,在多模塊項目中,視圖模塊作為最外層的運行模塊,也就是說views-demo這個模塊最后會被build成jar包(或者war包)運行在服務器上,作為最外層容器,當容器進行加載的時候會加載所有的application.properties文件,因為每個模塊都可能會有針對本模塊配置,我們要保證所有的模塊配置都要被SpringBoot加載,了解過SpringBoot的童鞋們都知道,SpringBoot的大部分配置項都可以在application.properties中進行直接配置,但是在views-demo加載所有模塊的application.properties文件的時候,由於名稱一致,這時就會出現覆蓋加載的問題,導致一部分的配置無法加載到,這時,就需要我們修改各個模塊的application.properties文件的名稱,保證所有模塊application.properties中的配置項都可以被SpringBoot加載;
這樣確實可以解決覆蓋加載的問題,但是會衍生出一個新的問題,就是SpringBoot默認只會去加載名稱為application.properties中的配置項,為了解決這個問題,我們可以使用@Profile注解去配置SpringBoot的加載環境,在每個模塊中都去做一個配置Bean,然后將所有修改過的資源文件都配置到views-demo中的application.properties文件中,使我們修改過名稱的application.properties文件都被SpringBoot加載;
basic-base模塊

service-demo1模塊

tools-common模塊

views-demo模塊

在views-demo模塊中統一加載修改過的資源文件

-
10.配置數據源:
在所有配置都完成之后,我們似乎可以運行項目了,但是其實還是最后一個地方需要進行配置,那就是配置數據源,不知道大家是否再記得,我們在配置SpringBoot的時候勾選了SQL塊中的Jpa和MySQL,如果不進行數據源配置的話運行就會拋出:Cannot determine embedded database driver class for database type NONE異常;
配置數據源以及其他基礎配置,配置完成之后我們運行views-demo項目,並進行build(打包:jar或war,我只做生成jar文件測試,平時服務器上也是部署jar文件)測試,如果項目無法build的話,說明程序還是存在問題的;
啟動測試


build測試是否可以生成jar文件,在build的時候可能會出現一個異常,是因為各個模塊中存在與main同級的test的問題,將test刪除即可

刪除各個模塊中的test后進行build,build成功后,在views-demo模塊的build->libs中會生成views-demo-0.0.1-SNAPSHOT.jar,我們將jar包直接在liunx環境下進行啟動,看是否可以成功運行;

運行WorkSpace中的views-demo-0.0.1-SNAPSHOT.jar


出現問題以及其他說明
項目結構:
basic-base(基礎模塊):所有業務模塊都需要用到的業務邏輯service;
tools-common(全局工具模塊):所有模塊需要的工具類,說到這,大家可能會有一個疑問,在上面的截圖中,大家會發現在每個模塊的入口處有一個包,包結構為:
pers.fly.common
- - - - - - - -|config
- - - - - - - -|tools
在項目的結構中已經存在了一個common的工具模塊,為什么每個包下還會存在tools這種工具包。又一次,我的一個朋友曾經和我說,在項目中你會發現有的工具類只有本項目才會用到,那為什么不在每個模塊中建立一個只放置本模塊的工具類的包呢,然后把所有模塊都會用到的工具類放到全局公共區域;這樣的規划的話顯然是更合理的;
service-demo1(業務模塊):此項目只為演示使用Gradle構建SpringBoot多模塊項目,在實際項目開發中,會存在多個業務模塊,所有業務模塊都已service-開頭,所以此項目中只有一個業務模塊,並且以demo1命名,在實際項目中最好不要出現數字,相關規則大家查看Java的命名規范,結合實際情況;
views-demo(視圖模塊):存放對外提供的接口,Controller接口的放置位置,針對具體的業務場景或者不同的終端;比如,這個視圖模塊只放置**的業務模塊的接口,或者只放置對APP端提供的接口,或者只放置對PC端提供的接口,或者只放置對微信端的接口等等;在實際項目中,視圖層模塊也可能存在多個;@Profile的使用:
學習過SpringBoot的童鞋肯定知道@Profile,在這我要說明一點,我在學習SpringBoot中的時候,網上的一些資料和書本中都有講解過@Profile的作用,大部分的資料和書籍說@Profile是為了方便區分項目環境而進行的配置,在實際項目中,項目環境會分為開發環境、測試環境、生產環境(標准的項目環境應該還會存在預發布環境),在這些環境中某些配置是不一樣的,比如數據庫的鏈接地址,連接池的配置或者等等其他的一些配置,然后使用@Profile是為了區分這些環境去配置一些不同的application.properties資源文件配置;我個人認為@Profile既然可以去做到將不同的環境區分,並且可以指定某個或同時指定多個環境的配置,那為什么只能作為項目環境的區分,如果要區分項目環境的話,有很多方法,比如在使用Git作為版本管理的時候,我們可以使用分支來作為區分,而且SpringBoot的配置文件的加載順序是從與項目平級的配置文件開始加載,然后在加載項目中的配置文件,在加載模塊中的配置文件,它的優先級是從外到內的(配置文件中,如果存在Java類配置的話Java類的優先級是高於application.properties的優先級的),在上不同的環境時我們可以在服務器上和jar包放置不同環境的application.properties文件也可以做到項目環境的區分;我還查閱了官方文檔,官方文檔是這樣描述的:
大概意思就是可以使用命名約定(application-{**}.properties)去加載、定義應用程序,官方文檔確實也使用了development、production去做一些例子,但個人認為@Profile不應該僅僅只是為了區分項目環境,最重要的是它可以靈活的去定義一些配置;配置完數據源之后還是會拋出Cannot determine embedded database driver class for database type NONE異常問題:
在使用Gradle構建SpringBoot項目的時候,出現過這樣的問題,在加載多個模塊的時候,明明配置了好了數據源也指定了數據庫的類型,但還是會拋出,並且在Run/Debug Configurations中確實是以Application方式啟動並且也指定了Working directory的項目地址,但是還是不行,后來發現將.idea刪除,重新使項目配置加載,然后這個問題就解決了,具體為什么我也不是特別明白,可能是idea的緩存?或者是Mac下idea的不兼容?我用的是Mac,不知道Windows下有沒有同樣的問題;關於build失敗的問題:
在進行build的時候會出現一個異常,在上面的截圖中build測試的時候也說了這個問題,拋出的異常信息顯示是關於測試文件的加載問題,具體為什么會出現這樣的問題,詳細原因目前為止還沒有找到,當前的解決方法就是刪除test模塊,刪除之后確實可以進行build,但是終歸不是長久之計,一個完整的項目怎么能沒有測試呢,這個問題接下來還是要處理一下;說明:以上均為個人見解,如果有不對的地方或者各位童鞋有不同的見解以及意見,歡迎留言指正~~

