一年前,當我和小夥伴小龍一塊兒作一個外包項目的時候,受到了嚴重的鄙視。我那時候還不知道 Maven,因此搭建項目用的仍是最原始的方式,小龍不得已在導入項目的時候花了很長時間去下載項目依賴的開源類庫。前端
出於對個人尊重,小龍沒有破口大罵,而是很是委婉地說了一句:「二哥,你好歹也有必定的知名度了,居然沒用 Maven 構建項目,真讓我大開眼界啊。」java
做爲一名富有上進心的程序員,不能忍啊。藉此機會,有必要隆重地向你們介紹一下 Maven 了。程序員
無論英文功底好很差,先看看官網給出的介紹語吧:web
Apache Maven is a software project management and comprehension tool. Based on the concept of a project object model (POM), Maven can manage a project's build, reporting and documentation from a central piece of information.spring
大體的意思就是說,Apache Maven 是一個項目管理和自動化構建工具,基於項目對象模型(POM)的概念,能夠管理項目的構建、報告以及文檔。做爲 Apache 組織中的一個頗爲成功的開源項目,Maven 主要服務於基於 Java 的項目構建、依賴管理和項目信息管理。apache
Maven 採用了約定優先配置的原則,這些原則以下表所示:app
目錄 | 目的 |
---|---|
${basedir} |
存放 pom.xml 和全部的子目錄 |
${basedir}/src/main/java |
存放 Java 源代碼 |
${basedir}/src/main/resources |
存放項目的資源文件,好比說 log4j.properties |
${basedir}/src/test/java |
存放測試類 |
${basedir}/src/test/resources |
存放測試用的資源 |
${basedir}/src/main/webapp |
存放 Web 前端文件 |
${basedir}/target |
項目打包後的輸出目錄 |
${basedir}/target/classes |
項目編譯後輸出目錄 |
~/.m2/repository |
默認的 Maven 倉庫目錄(~表示用戶目錄) |
使用約定優先配置帶來的最大好處就是項目的目錄結構圖很是的統一,不一樣的開發者在開發一個 Maven 項目的時候,文件存放位置幾乎沒有差異,省去了不少沒必要要的麻煩,有利於促進項目團隊的標準化。webapp
咱們這個年代很是崇尚開源精神,幾乎全部的 Java 項目都會借用一些第三方的開源類庫,這些類庫能夠經過依賴的方式引入到項目中來。但隨着依賴的增多,版本衝突、依賴臃腫的問題就會接踵而來。手工解決這些問題是十分枯燥的,幸運的是 Maven 提供了一個優秀的解決方案,它經過一個三維的座標(<groupId>
、<artifactId>
、<version>
)來準確地定位每個開源類庫。maven
另外,我認爲 Maven 特別優秀的一點是,它把項目依賴的全部開源類庫都從遠程中央倉庫下載到了指定的本地倉庫中,也就是說,這些開源類庫能夠在多個項目之間共用,無需重複下載——假如我用 Maven 構建項目的話,小龍就不用下載那麼多開源類庫了,他的本地倉庫中可能已經有了——我也就不會被鄙視了。ide
1)安裝 Maven 以前,先確保電腦上已經安裝了 JDK。
2)去 Maven 官網下載想要的版本並解壓,下載地址爲:
3)設置環境變量,主要是 MAVEN_HOME 和 Path。
4)打開命令行,輸入 mvn -v
驗證 Maven 是否配置成功。
5)Maven 的 conf 目錄下包含了一個很是重要的文件 settings.xml,通常狀況下,我傾向於將該文件複製到 ~/.m2/
目錄下——建議你也這麼作。
打開該文件,在 <mirrors></mirrors>
節點下添加阿里雲的鏡像地址(參照下面的代碼)。爲何要這麼作呢?由於 Maven 默認的倉庫在不翻強的狀況下很難訪問到。
<mirror>
<id>alimaven</id>
<name>aliyun maven</name>
<url>http://maven.aliyun.com/nexus/content/groups/public/</url>
<mirrorOf>central</mirrorOf>
</mirror>
複製代碼
這裏須要注意的是,<mirrorOf>
的值有下面四種方式:
<mirrorOf>*<mirrorOf>
:匹配全部遠程倉庫,也就是說任何對於中央倉庫的請求都會轉至該鏡像。<mirrorOf>external:*<mirrorOf>
:匹配全部不在本機上的遠程倉庫。<mirrorOf>repo1,repo2<mirrorOf>
:匹配倉庫 repo1 和 repo2,使用逗號分隔多個遠程倉庫。<mirrorOf>*,!repo<mirrorOf>
:匹配全部遠程倉庫,repo 除外,使用感嘆號將倉庫從匹配中排除。6)在 Eclipse 下依次選擇菜單 Window → Show View → Other → Maven → Maven Workspace Build,查看鏡像是否配置成功(我習慣了使用 Eclipse,因此請見諒,不過無論使用哪一種集成開發環境,思路和步驟都大差不差)。
爲了儘快步入重點,這一小節我會有意的拈輕怕重,不必的步驟會略過。
1)在 Eclipse 中新建項目的時候選擇 Maven Project。
2)在接下來選擇項目類型的時候,選擇 maven-archetype-quickstart,以下圖所示。
3)而後指定項目參數的時候填寫 group id 和 artifact id。
4)項目建立成功後的目錄結構圖以下圖所示。
Maven 3 默認使用的依然是 JDK 1.5,不過咱們能夠爲其配置更高版本的 JDK,後面會聊到。
毫無疑問,Maven 項目的靈魂只有一個,那就是 pom.xml 文件,因此接下來我會詳細地對其進行分析。
1)項目基本信息
pom.xml 文件的第一部分主要用來描述項目的基本信息。
<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/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.cmower</groupId>
<artifactId>test</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
<name>test</name>
</project>
複製代碼
①、<project>
是 pom.xml 的根元素,聲明瞭相關的命名空間。
②、<modelVersion>
指定了當前項目對象模型(POM)的版本,對於 Maven 3.x 來講,該值只能是 4.0.0。
③、<groupId>
定義了項目的組名,這個組每每和項目所在的組織或公司關聯。
④、<artifactId>
定義了當前 Maven 項目在組中惟一的 ID。
⑤、<version>
定義了項目的版本號,SNAPSHOT
爲快照的意思,也就是說該項目還處於開發階段。
⑥、<packaging>
定義了項目的打包類型,可選值有 war、jar 等。
⑦、<name>
定義了項目的名稱。
2)變量配置信息
pom.xml 文件的第二部分一般用來配置一些變量信息。
<properties>
<spring.version>5.1.5.RELEASE</spring.version>
</properties>
複製代碼
有了變量的配置信息後,能夠經過 ${spring.version}
的形式來調用這些配置項。這樣作的好處顯而易見,當依賴項的版本升級的時候,能夠直接修改變量值便可。
3)依賴管理
阿里雲的 Maven 倉庫下有各類各樣的第三方類庫,換句話說就是,只有你想不到的,沒有你找不到的。大多數 Maven 項目的依賴項列表都會很長很長,爲了便於說明,下面我只列出某些具備特點的。
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>3.8.1</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-core</artifactId>
<version>${spring.version}</version>
<exclusions>
<exclusion>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>commons-logging</groupId>
<artifactId>commons-logging</artifactId>
<version>1.1.1</version>
</dependency>
</dependencies>
複製代碼
①、上文中曾提到,<groupId>
、<artifactId>
、<version>
合起來能夠準確地定位一個依賴項。那怎麼找到想要的依賴項呢?
第一步,進入 MavenRepository 網站,地址以下:
而後在搜索框中輸入第三方類庫的關鍵字,好比說「spring-core」,點擊「search」按鈕,能夠查看到該類庫的連接導航。
第二步,點擊連接進入到「spring-core」的主頁,能夠看到全部版本的「spring-core」,選擇一個使用率最高的。使用率高在必定程度上代表這個版本的類庫最穩定,它已經獲得了廣大程序員的承認。
第三步,進入該版本的主頁,只須要左鍵輕輕地在 「Maven」選項卡內點一下,就已經把該類庫的 Maven 依賴信息複製到粘貼板了(不須要「Ctrl+C」,很是的人性化),以下圖所示。
第四步,將類庫的依賴信息粘貼到 pom.xml 文件的 <dependencies>
節點下,而後按下快捷鍵「Ctrl+S」保存。緊接着,依次展開 test → Java Resources → Libraries → Maven Dependencies 節點,你能夠看到該類庫已經悄悄地添加進來了。
②、 <exclusions>
主要用於排除依賴。
有時候,咱們引入的依賴中可能會包含一些不想要的依賴包,咱們想引入本身想要的,這時候就要用到排除依賴了。
使用 <exclusion>
的時候只須要指定 groupId 和 artifactId 就好了,並不須要 version,這是由於 groupId 和 artifactId 就能夠定位某種類型的依賴。
③、 <scope>
用來控制依賴的範圍。
test:測試依賴範圍。典型的例子是 Jnuit,它只有在編譯測試代碼及運行測試的時候才須要。
compile:編譯依賴範圍(其實不止是編譯,對測試、運行一樣有效),缺省項,若是沒有指定,就會默認使用該依賴範圍。
provided:提供依賴範圍。對編譯和測試有效,但在運行時候無效。
runtime:運行時依賴範圍。對測試和運行有效,但在編譯時無效。
PS:若是不知道選哪種,缺省就對了。
4)構建配置
<build>
元素中包含了執行 Maven 構建週期目標所需的插件以及相關的配置。
<build>
<finalName>test</finalName>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>2.3.2</version>
<configuration>
<source>${jdk.version}</source>
<target>${jdk.version}</target>
</configuration>
</plugin>
</plugins>
<resources>
<resource>
<directory>src/main/java</directory>
<includes>
<include>**/*.xml</include>
</includes>
</resource>
</resources>
</build>
複製代碼
①、<finalName>
,打成 jar 包或者 war 包時的名稱。上文中曾提到,項目打包後的輸出目錄爲 ${basedir}/target
。
②、<plugins>
用於指定項目在構建過程當中使用的插件。
<groupId>
、<artifactId>
、<version>
用於肯定使用的插件。<configuration>
,該插件所須要的特殊配置。Maven 3 默認使用的是 JDK 1.5,本例中咱們使用了 JDK 1.8。③、<resources>
描述了各個資源在 Maven 項目中的具體路徑。
<directory>
,資源文件的路徑,默認位於 ${basedir}/src/main/resources/
目錄下。<includes>
,用於指定在構建過程當中被處理的資源文件;對應 <excludes>
用於省去不被處理的資源文件。1)清理:mvn clean
,該命令會刪除 target 目錄。能夠直接在命令行中執行該命令,只須要切換到項目所在的路徑下便可。
2)編譯:mvn complie
,該命令會編譯 src/main/java 目錄下的源碼。同時,Maven 還會處理在 src/main/resources 目錄下的資源文件,確保它們做爲編譯的一部分。
不過,很遺憾的是,執行該命令會報錯。該命令給出的提示是,查看 [Help 1] 給出的地址,我嘗試了一下,能夠將 mvn complie
命令替換爲 mvn compiler:compile
命令執行,結果以下圖所示。
編譯後能夠在 target 目錄下查看字節碼文件。
3)測試:mvn test
,test 命令在運行時,會執行 compile 命令;而以前咱們已經執行過一次 compile 命令,爲了確保結果的準確性,能夠執行 mvn clean test
命令確保測試以前沒有殘餘物,結果以下圖所示。
Maven 會經過 Surefire 插件,使用 pom.xml 文件中的測試提供者(一般是 Junit)運行測試。執行 test
命令不只會運行測試,還會產生報告文件,此時 target 目錄下的截圖以下:
4)打包:mvn install
,該命令會按照 pom.xml 文件中 <packaging>
指定的方式(本例爲 jar)對編譯結果打包。同時,還會把打包好的文件放到本地的 Maven 倉庫中,以便其餘項目把它當作依賴項使用。命令執行結果以下圖所示。
查看本地的 Maven 倉庫,能夠看到剛剛打包好的文件。
在 Maven 出現以前,流行的構建工具是 Ant;在 Maven 出現以後,還有一種新興的構建工具 Gradle,它有意選擇了和 Maven 相反的原則,不會強制使用者遵循刻板的構建週期。
總之,Maven 是一款優秀的構建工具,Java 項目的開發者頗有必要熟練地掌握它。
PS:掃碼關注「沉默王二」公衆號,回覆關鍵字「0」獲取二哥精心準備的程序員進階電子書大禮包。