看到一份2018 年 JVM 生態報告提到,使用構建工具的比例,maven高達60%,遠高於gradle的19%。html
我日常也使用maven,因而就整理了一些maven的經常使用知識。
關於maven的博文已經浩如煙海 ,因此這裏我只是總結一些本身經常使用知識,以作備忘。web
分爲本地倉庫和遠程倉庫
遠程倉庫默認使用的是 Maven 社區提供的中央倉庫apache
還有其餘社區提供的倉庫,如jcenter,jboss。
通常公司都會使用Nexus部署一個私服(也是倉庫),用於存放公司內部構件。
mvn deploy 能夠將項目生成的構件分發到私服。緩存
由於中央倉庫通常部署在外國,下載構件速度比較慢,因此能夠經過鏡像mirror下載, mirrorOf配置代理倉庫。
當須要從代理倉庫下載構件時,都會轉爲從鏡像下載。
鏡像中不存在該構件時,鏡像會從倉庫下載,緩存到鏡像中。
須要注意的是,因爲鏡像徹底屏蔽了代理倉庫,當鏡像不穩定或者中止服務的時候,Maven不會直接訪問代理倉庫,於是將沒法下載構件。
最經常使用的是阿里提供的鏡像服務:tomcat
<mirror> <id>nexus-aliyun</id> <mirrorOf>central</mirrorOf> <name>Nexus aliyun</name> <url>http://maven.aliyun.com/nexus/content/groups/public</url> </mirror>
profile用於定義不一樣環境的不一樣配置,如開發,測試環境使用不一樣的倉庫,打包方式等。
mvn clean package -Ppro即構建出pro環境須要的war包app
構造Java項目mvn archetype:generate -DinteractiveMode=false -DgroupId=com.binecy -DartifactId=my-core
webapp
構造Web項目mvn archetype:generate -DinteractiveMode=false -DarchetypeArtifactId=maven-archetype-webapp -DgroupId=com.binecy -DartifactId=my-web
maven
構造子模塊
構造父模塊# mvn archetype:generate -DinteractiveMode=false -DgroupId=com.binecy -DartifactId=system-core
進入system-core項目# cd system-core
刪除不須要的src文件夾# rm src
工具
修改pom.xml文件,將<packaging>jar</packaging>修改成<packaging>pom</packaging>
構造子模塊system-dao# mvn archetype:generate -DinteractiveMode=false -DgroupId=com.binecy -DartifactId=system-dao
構造子模塊system-web# mvn archetype:generate -DinteractiveMode=false -DgroupId=com.binecy -DartifactId=system-web
測試
這時父模塊的pom.xml已經自動添加了module信息
<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.binecy</groupId> <artifactId>system-core</artifactId> <packaging>pom</packaging> <version>1.0-SNAPSHOT</version> <name>system-core</name> <url>http://maven.apache.org</url> <modules> <module>system-service</module> <module>system-web</module> </modules> </project>
一個多模塊的項目構造完成。
dependencyManagement
父模塊中定義的dependencies,子模塊默認繼承,不需重複定義也可使用。
父模塊中定義的dependencyManagement只是聲明依賴,並不實現引入,若是子模塊也定義了該依賴,能夠繼承父模塊dependencyManagement中定義的version和scope,不用須要聲明這兩個屬性。
若是子模塊也聲明瞭version屬性,則使用子模塊聲明的版本。
跳過測試mvn install -Dmaven.test.skip=true
使用tomcat插件
<plugin> <groupId>org.apache.tomcat.maven</groupId> <artifactId>tomcat7-maven-plugin</artifactId> <version>2.2</version> <configuration> <path>/</path> <port>9090</port> <uriEncoding>UTF-8</uriEncoding> </configuration> </plugin>
依賴傳遞
若是咱們的項目A依賴構件B,而構件B又依賴於構件C,依賴的關係爲:A—>B—>C
當咱們執行項目A,maven會下載構件B,構件C
依賴衝突
若是有一下依賴關係
A—>B—>C(version:0.0.1)
A—>D>—C(version:0.0.2)
那麼項目A引入哪一個版本的構件C呢?
這裏有兩個重要的依賴調解原則。
1:若是依賴路徑的長度不一樣,則「短路優先」:
A—>B—>C—>D—>E—>X(version 0.0.1) A—>F—>X(version 0.0.2) 則A依賴於X(version 0.0.2)。
2:依賴路徑長度相同狀況下,則「先聲明優先」:
A—>E—>X(version 0.0.1) A—>F—>X(version 0.0.2) 若是項目A的depencies先聲明引入E,這A依賴於X(version 0.0.1)
依賴衝突,一般是低版本的依賴覆蓋了高版本的依賴,而某些構件使用了高版本特有的功能致使的。這時可使用dependency:tree分析依賴關係,使用exclusions排除重複的依賴或者添加優化級更高的正確依賴。
參考:
Maven 核心原理