網上搭建maven環境的文檔有不少,這裏就不贅述了html
具體能夠參看http://www.cnblogs.com/quanyongan/archive/2013/04/17/3025971.htmljava
下面開始上手mavenapache
首先咱們先了解一下maven的目錄結構編程
一般的maven工程的目錄結構是這樣的,最頂層是咱們的src目錄,也就是咱們放置源代碼的目錄。下面的是main,和與其平行的test目錄。 main下面是java,java下面是咱們自定義的包。test下面也是一個java,下面也是package。和main,test相平行的是resource目錄,這個目錄一般是用來存放資源文件的,可是本例中並無引用其餘資源,因此沒有建立resource目錄服務器
下面是全套的國際標準的maven目錄結構 你們看下方便查閱:網絡
下面就按照剛纔介紹的目錄結構,在本地計算機上手動創建一下文件夾,別怕麻煩,這樣有助於使你們的思路更加清晰框架
就像我這樣創建eclipse
寫咱們的HelloMaven類:maven
package com.kfh.model; public class HelloMaven { public String sayHello() { return "Hello Maven!"; } }
接下來咱們寫一個測試類放在與main平級的test文件夾下得java下面:ide
package com.kfh.test; import com.kfh.model.*; import org.junit.*; public class HelloManvenTest { public void testHello() { Assert.assertEquals("Hello Maven!", new HelloMaven().sayHello()); } }
這樣咱們代碼就寫完了,最後呢咱們須要一個pom.xml來管理咱們的項目。
pom.xml從哪裏找呢,咱們能夠從隨便一個maven項目中拷貝一個pom.xml, 好比從Struts目錄下面就有
找到Struts2-core這個包裏面的META-INF中的pom
刪除一些咱們不用的東西,又由於咱們用到了junit4 因此在pom中添加對junit的依賴造成了以下pom.xml:
<?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.kfh.model</groupId> <artifactId>maven01</artifactId> <version>0.0.1SNAPSHOT</version> <dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.10</version> </dependency> </dependencies> </project>
其中 modelVersion指的是 maven的版本,是4.0.0,這個是固定的。 groupId指的是咱們的包名,artifactId的值指的是模塊的名字,建議使用項目名字。版本是0.0.1SNAPSHOT,指的是項目的版本是0.0.1快照的版本
咱們須要記住:
GroupID是項目組織惟一的標識符,實際對應JAVA的包的結構,是main目錄裏java的目錄結構。
ArtifactID就是項目的惟一的標識符,實際對應項目的名稱,就是項目根目錄的名稱。
通常GroupID就是填com.leafive.test這樣子。
寫好pom.xml以後把他放到項目下面,與src文件夾平行的位置
打開命令行,進入項目的根路徑下面 個人是F:\mavenTest,輸入mvn complie對該項目進行編譯
注意 mvn compile 編譯的是項目的源碼 也就是src目錄下面java下面的代碼。
輸入mvn test 運行test下面的測試類
這說明咱們測試成功了,這時咱們點開項目根目錄 mavenTest下面,發現多了一個target文件夾,點進去發現,這裏存放了咱們編譯事後的.class文件.
咱們繼續在根目錄F:\mavenTest輸入 mvn package ,成功後,發如今target文件夾下面生成了一個jar文件,後綴是Executable Jar File,這就是咱們所謂的打包成jar文件。
重點掌握mvn -install 舉個例子,這個例子中咱們要用到上一個例子中的類,因此要添加項目1中的依賴,用到install命令:
依舊按照剛纔的方法手動創建maven目錄結構,建立maven02項目, 分別在src->main->java->com->kfh->util->下面創建 Speak類 和相應的測試類src->test->java->com->kfh->util->SpeakTest兩個類,其中咱們在Speak中要用到剛剛的mavenTest中的HelloMaven這個類
因此咱們這樣寫:
Speak類:
package com.kfh.util; import com.kfh.model.*; public class Speak { public String sayHi() { return new HelloMaven().sayHello(); } }
SpeakTest:
package com.kfh.util; import com.kfh.model.*; import org.junit.*; public class SpeakTest { @Test public void testSayHi() { Assert.assertEquals("Hello Maven!", new Speak().sayHi()); } }
這時候咱們在maven02項目中編譯項目,mvn complie,會報錯,找不到類 model,此處咱們就用到了mvn install的命令了,須要用mvn install 將mavenTest添加到本地maven倉庫中,而後再在maven02中添加mavenTest的依賴。
從命令提示符進入mavenTest目錄,執行mvn install,修改maven02的pom.xml以下,添加一個上一個項目的依賴, 添加一個依賴只須要把這個資源的座標添加到dependencies就能夠了,也就是groupId, artifaceId, version這三個就標識了一個資源。
<?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.kfh.util</groupId> <artifactId>maven02</artifactId> <version>0.0.1SNAPSHOT</version> <dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.10</version> </dependency> <dependency> <groupId>com.kfh.model</groupId> <artifactId>maven01</artifactId> <version>0.0.1SNAPSHOT</version> </dependency> </dependencies> </project>
再進入maven02目錄編譯就能成功了。
經過本例子能夠體會出,maven在構建項目進行編譯的時候是,缺乏依賴包是從pom.xml中查找的。
重點來了:maven構建項目的一個大體流程是這樣的:
在咱們進行項目編譯的時候,若是項目用到了其餘的依賴包,maven就會從pom中查找是否有該依賴包的座標,也就是groupId, artifaceId, version這三個,若是有,就會從本地倉庫中找到該資源並加入到項目的classpath中,若是沒有,就會從maven的中心倉庫查找並下載該依賴包。
每次手動建立maven的目錄結構是在是太麻煩了,這裏能夠用archetype插件自動建立符合maven規定的目錄骨架。
咱們先建立一個項目用於存放代碼,叫作maven03。
打開命令提示符,進入maven03 根目錄。使用 mvn archetype:generate命令生成目錄
第一次使用該插件,maven會下載一些相關的依賴
下載好後,會提示你輸入本項目的 groupId, artifactId 和 version,回車後項目骨架就建立好了。咱們能夠看到插件除了生成了項目結構之外還生成了一個App.java,其中輸出了Hello World。
測試一下 ,進入maven03 根目錄 mvn compile進行編譯,再用mvn exec:java -Dexec.mainClass="com.kfh.maven03.service.App" 運行maven項目,輸出hello world說明咱們成功了。
在maven世界中任何一個插件,依賴,均可以被稱之爲構件,全部構件均經過座標做爲其惟一標識。
groupId, artifactId, version 做爲這個構件的惟一標識。建議你們使groupId和包名(公司域名的反寫+項目名字)是一致的,artifactId是項目名+模塊的名字。這樣看起來更加富有邏輯。
如此多的構件,他們都是存儲在哪裏呢?是maven倉庫中。maven倉庫就是管理項目的依賴的,倉庫分爲本地倉庫和遠程倉庫。若是maven在本地倉庫中找不到咱們須要的構件的時候,他會去maven全球遠程的中央倉庫中查找。找到了就會下載到本地倉庫中以供使用。遠程倉庫中也找不到的話就會報錯,maven提供了一個默認的遠程中央倉庫地址。在 maven的安裝目錄中lib下面的maven-model-builder.jar這個jar中有個超級pom-4.0.0.xml,咱們之後的pom都是默認繼承了這個pom的,打開它能夠看到以下url就是咱們的maven中央倉庫地址:
所謂鏡像倉庫,就是maven中心倉庫的複製,由於maven中心倉庫在國外的服務器,有時候會出一些網絡問題,這就須要咱們使用一個國內的鏡像倉庫,保證穩定。如何修改maven倉庫的位置呢?
打開maven安裝目錄,找到conf,setting.xml ,找到<mirror> 標籤,配置這個標籤就能夠了。
也能夠在項目的pom.xml中加入一個repository 以下:
<repositories> <repository> <id>custom</id> <url>http://119.254.111.62:8081/nexus/content/groups/public</url> </repository> </repositories>
仍是找到conf下面的settings.xml 修改 localRepository標籤的路徑便可
<localRepository>/path/to/local/repo</localRepository>
若是你的eclipse是4.0以上的版本能夠不用安裝mavne插件了,如下的版本就得手動安裝插件了。
咱們新建一個maven project 隨便起一個名字:
finish 以後,能夠看到maven項目的目錄已經搭建好了
咱們來測試一下 eclipse生成的maven project是如何運行的。
右鍵 pom.xml 選擇 maven build 在Goals中輸入 compile命令 點run 按鈕讓maven去編譯項目
若是編譯成功了就能夠看到已經生成了classes文件了。
同理,若是在Goals中輸入package命令,maven就會爲咱們把項目進行打包操做,在target中生成了jar文件。
一個項目有他完整的生命週期,如清理、編譯、測試、打包、集成測試、驗證、部署等。
在maven中對應的抽象出了maven的生命週期,而插件呢就是maven生命週期的具體體現。
好比maven中執行編譯命令,這是出於maven一個生命週期之中的,是由maven-compile-plugin實現的。
maven中定義了3套相互獨立的生命週期:
clean 清理項目
default 構建項目
site 生成項目站點
其中每一個生命週期呢是相互獨立的,每一個生命週期又分爲幾個階段,在這幾個階段中後面的階段又依賴於前面的階段。執行某個階段的時候,其前面的階段會依次順序執行。但不會觸發另外兩套生命週期的任何階段。
舉個例子:
好比咱們以前執行過這麼幾個命令:
clean、compile、test、package、install
咱們執行package這個階段以前呢,compile和test是依次執行的。
對於clean呢,又分爲三個階段
pre-clean 執行清理前的工做
clean 清理上一次構建生成的全部文件
post-clean 執行清理後的文件
default構建項目最核心的部分,階段比較多,平時遇到最多的有如下幾種,好比:
compile test package install
這些都屬於default生命週期
site生成項目站點
pre-site 在生成項目站點前要完成的工做
site 生成項目的站點文檔
post-site 在生成項目站點後要完成的工做
site-deploy 發佈生成的站點到服務器上
1.根元素 project
2.modelVersion 固定版本4.0.0 指定了當前pom的版本
3.座標 <groupId>,<artifactId>,<version>,<packageing>
groupId 反寫的公司網址+項目名
artifactId 項目名+模塊名
version 版本號 第一個0表示大版本號,第二個0表示大版本號,第三個0表示大版本號。如:0.0.1snapshot快照。
(snapshot 快照/alpha 內部測試/beta 公測/Release穩定/GA正式發佈)
packaging 打包方式 默認是jar
4. name :項目描述名
url:項目的地址
description:項目描述
developers:開發人員列表
licenses:許可證
organization:組織信息
5.dependency的
<optional>:設置依賴是否可選
<exclusions>:排除依賴傳遞列表(A->B->C,可排除C)
6.dependencyManagement管理,僅僅啓到定義的做用,用於定義parent,子模塊繼承。
7.build-plugins 插件列表
8.parent 、 modules
maven提供了三種classpath 編譯、測試、運行
這裏的scope指的是此依賴存在的範圍,junit咱們設置的是test,因此junit只存在於測試的classpath中
因此scope便是用來管理依賴和classpath的關係的。classpath不懂的能夠參看個人一篇關於classpath的介紹的博文http://my.oschina.net/u/2561483/blog/600660
依賴:就是咱們編程時須要使用到的他人爲咱們提供好的程序,各類框架、各類庫、各類API、各類工具包等等都是這樣的。對於JAVA編程而言,咱們須要將這些程序(打好的JAR包,放到classpath路徑下就能夠了)Maven爲咱們提供了三種classpath,編譯、運行、測試,因此就進一步的產生了依賴範圍這個概念,就是指這三種classpath在何時有效,下面是依賴範圍(三種classpath有效的性的一個劃分)的六種分類:<br>
1.compile:默認範圍,編譯測試運行都有效<br>
2.provided:在編譯和測試時有效<br>
3.runtime:在測試和運行時有效<br>
4.test:只在測試時有效<br>
5.system:在編譯和測試時有效,與本機系統關聯,可移植性差<br>
6.import:導入的範圍,它只使用在dependencyManagement中,表示從其餘的pom中導入dependency的配置
這裏只是一個入門的講解,若是想深刻的瞭解這個工具的使用方式,應該去官網讀文檔,而且在實際的工做中多多的使用使用,纔是關鍵。
傳遞依賴:簡單講就是間接依賴關係,好比:B依賴A,C依賴B,那麼C也就依賴A了,C和A的依賴關係就是傳遞依賴。<br>
Maven對於依賴的管理是這樣的,當在POM.XML文件中發現配置了,某個依賴,就先去本身本地的依賴倉庫中去找對應的依賴,若是沒找到,就去Maven的中央依賴倉庫中去找,若是仍是沒找到,就會生氣報錯。<br>
對於項目而言,好比上面的例子A/B/C咱們須要在B的POM.XML依賴關係中配置上A的座標,而且須要對A進行編譯、打包、安裝到本地倉庫等工做,B才能實現對A的依賴。C依賴與B,而且B依賴與A,C的依賴庫裏會自動的將A項目的jar包也導進來的。若是咱們不想這樣,那麼就須要用到排除依賴這個標籤了<exclusion></exclusion>——此標籤就是排除對傳遞依賴的依賴關係的一種方式。
另外,在settings.xml文件中能夠設置maven默認jre版本——使用<profile></profile>標籤
依賴衝突:是指間接依賴關係中依賴同一個依賴,或者同一個依賴的不一樣版本的狀況,此時咱們就須要判斷到底依賴那一個依賴,以下是選擇的兩條原則。<br>
<br>
若是A經過依賴傳遞的關係經過不一樣的路徑依賴同一個依賴B。<br>
①:短路優先:<br>
會優先解析路徑短的版本,好比:<br>
A -> B -> C -> X(jar)<br>
A -> D -> X(jar) 優先解析短的<br>
②:先聲明先優先<br>
若是路徑長度相同,則誰先聲明,先解析誰——根據在依賴文件POM.XML中聲明的前後順序來選擇依賴
聚合:若是項目D依賴項目C,項目C依賴項目B,項目B依賴項目A,咱們須要一個個安裝這項項目,在Maven中有一種方式能夠將多個項目一次性安裝,這就是聚合的概念。簡單講就是,須要人工屢次操做的,只要MAVEN能理解,一次性告訴他,他就能幫咱們作這件單調煩人的事情了。——使用<modules></modules>這個標籤
繼承:屢次使用到的依賴,好比:單元測試,沒有必要在全部的項目中都引用一下,此時就能夠採用繼承的方式來實現,先來一個父級的POM.XML而後再繼承此POM.XML