1. 程式人生 > >Maven座標詳解。

Maven座標詳解。

Maven座標為各種構件引入了秩序,任何一個構件都必須明確定義自己的座標,而一組Maven座標是通過一些元素定義的,他們是groupId、artifactId、version、packaging、classifier。先看一組座標定義,如下:

<groupId>org.sonatype.nexus</groupId>
<artifactId>nexus-indexer</artifactId>
<version>2.0.0</version>
<packaging>jar</packaging>

這是nexus-indexer的座標定義,nexus-indexer是一個對Maven倉庫編篡索引並提供搜尋的類庫,他是Nexus專案的一個子模組。上述程式碼片段中,其座標分別為groupId:org.sonatype.nexus、artifactId:nexus-indexer、version:2.0.0.、packaging:jar,沒有classifier。下面詳細解釋一下各個座標元素。

groupId

定義當前Maven專案隸屬的實際專案。首先,Maven專案和實際專案不一定是一對一的關係。比如SpringFramework這一實際專案,其對應的Maven專案會有很多,如spring-core、spring-context等。這是由於Maven中模組的概念,因此,一個實際專案往往會被劃分成很多模組。其次,groupId不應該對應專案隸屬的組織或公司。原因很簡單,一個組織下會有很多實際專案,如果groupId只定義到組織級別,而後面我們會看到,artifactId只能定義Maven專案(模組),那麼實際專案這個層將難以定義。最後,groupId的表示方式與Java包名的表示方法類似,通常與域名反向一一對應。上例中,groupId為org.sonatype.nexus,org.sonatype表示Sonatype公司建立的一個非營利性組織,nexus表示Nexus這一實際專案,該groupId與域名nexus.sonatype.org對應。

artifactId

該元素定義實際專案中的一個Maven專案(模組),推薦的做法是使用實際專案名稱作為artifactId的字首。比如上例中的artifactId是nexus-indexer,使用了實際專案名nexus作為字首,這樣做的好處是方便尋找實際構件。在預設情況下,Maven生成的構件,其檔名會以artifactId作為開頭,如nexus-indexer-2.0.0.jar,使用實際專案名稱作為字首之後,就能方便從一個lib資料夾中找到某個專案的一組構件。考慮有5個專案,每個專案都有一個core模組,如果沒有字首,我們會看到很多core-1.2.jar這樣的檔案,加上實際專案名字首之後,便能很容易區分foo-core-1.2.jar、bar-core-1.2.jar......

version

該元素定義Maven專案當前所處的版本,如上例中nexus-indexer的版本是2.0.0。需要注意的是,Maven定義了一套完成的版本規範,以及快照(SNAPSHOT)的概念。

packaging

該元素定義Maven專案的打包方式。首先,打包方式通常與所生成構件的副檔名對應,如上例中packaging為jar,最終的檔名為nexus-indexer-2.0.0.jar,而使用war打包方式的Maven專案,最終生成的構件會有一個.war檔案,不過這不是絕對的。其次,打包方式會影響到構建的生命週期,比如jar打包和war打包會使用不同的命令。最後,當不定義packaging的時候,Maven會使用預設值jar。

classifier

該元素用來幫助定義構建輸出的一些附屬構建。附屬構件與主構件對應,如上例中的主構件是nexus-indexer-2.0.0.jar,該專案可能還會通過使用一些外掛生成如nexus-indexer-2.0.0-javadoc.jar、nexus-indexer-2.0.0-sources.jar這樣一些附屬構建,其包含了Java文件和原始碼。這時候,javadoc和sources就是這兩個附屬構建的classifier。這樣,附屬構建也就擁有了自己唯一的座標。還有一個關於classifier的典型例子是TestNG,TestNG的主構件是基於Java1.4平臺的,而他又提供了一個classifier為jdk5的附屬構件。注意,不能直接定義專案的classifier,因為附屬構建不是專案直接預設生成地,而是由附加的外掛幫助生成。

上述5個元素中,groupId、artifactId、version是必須定義的,packaging是可選的(預設為jar),而classifier是不能直接定義的。

同時,專案構建的檔名和座標相對應的,一般的規則為artifactId-version [-classifier] .packaging,[-classifier]表示可選。比如上例nexus-indexer的主構件為nexus-indexer-2.0.0.jar,附屬構建有nexus-indexer-2.0.0-javaodc.jar。這裡還要強調一點是,packaging 並非一定與構件副檔名對應,比如packaging為maven-plugin的構件副檔名為jar。

此外,Maven倉庫的佈局也是基於Maven座標。