maven介紹 極客學院

來自極客學院html

Apache Maven 是一套軟件工程管理和整合工具。基於工程對象模型(POM)的概念,經過一箇中央信息管理模塊,Maven 可以管理項目的構建、報告和文檔。前端

 

Maven - 概述

 

Maven 是什麼?

 

Maven 是一個項目管理和整合工具。Maven 爲開發者提供了一套完整的構建生命週期框架。開發團隊幾乎不用花多少時間就可以自動完成工程的基礎構建配置,由於 Maven 使用了一個標準的目錄結構和一個默認的構建生命週期。java

 

在有多個開發團隊環境的狀況下,Maven 可以在很短的時間內使得每項工做都按照標準進行。由於大部分的工程配置操做都很是簡單而且可複用,在建立報告、檢查、構建和測試自動配置時,Maven 可讓開發者的工做變得更簡單。web

 

Maven 可以幫助開發者完成如下工做:spring

 

  • 構建
  • 文檔生成
  • 報告
  • 依賴
  • SCMs
  • 發佈
  • 分發
  • 郵件列表

 

總的來講,Maven 簡化了工程的構建過程,並對其標準化。它無縫銜接了編譯、發佈、文檔生成、團隊合做和其餘任務。Maven 提升了重用性,負責了大部分構建相關的任務。數據庫

 

Maven 的歷史

 

Maven 最初是在 Jakarta Turbine 項目中爲了簡化構建過程而設計的。項目中有幾個子工程,每一個工程包含稍有不一樣的 ANT 文件。JAR 文件使用 CVS 管理。apache

 

Apache 小組隨後開發了 Maven,可以同時構建多個工程、發佈工程信息、部署工程、在幾個工程中共享 JAR 文件,而且協助團隊合做。windows

 

Maven 的目標

 

Maven 的主要目的是爲開發者提供api

 

  • 一個可複用、可維護、更易理解的工程綜合模型
  • 與這個模型交互的插件或者工具

 

Maven 工程結構和內容被定義在一個 xml 文件中 - pom.xml,是 Project Object Model (POM) 的簡稱,此文件是整個 Maven 系統的基礎組件。詳細內容請參考 Maven POM 部分。服務器

 

約定優於配置

 

Maven 使用約定而不是配置,意味着開發者不須要再本身建立構建過程。

 

開發者不須要再關心每個配置細節。Maven 爲工程提供了合理的默認行爲。當建立 Maven 工程時,Maven 會建立默認的工程結構。開發者只須要合理的放置文件,而在 pom.xml 中再也不須要定義任何配置。

 

舉例說明,下面的表格展現了工程源碼文件、資源文件的默認配置,和其餘一些配置。假定 ${basedir} 表示工程目錄:

 

配置項
默認值
source code ${basedir}/src/main/java
resources ${basedir}/src/main/resources
Tests ${basedir}/src/test
Complied byte code ${basedir}/target
distributable JAR ${basedir}/target/classes

 

爲了構建工程,Maven 爲開發者提供了選項來配置生命週期目標和工程依賴(依賴於 Maven 的插件擴展功能和默認的約定)。大部分的工程管理和構建相關的任務是由 Maven 插件完成的。

 

開發人員不須要了解每一個插件是如何工做的,就可以構建任何給定的 Maven 工程。詳細內容請參考 Maven 插件部分。

 

 

Maven - POM

POM 表明工程對象模型。它是使用 Maven 工做時的基本組建,是一個 xml 文件。它被放在工程根目錄下,文件命名爲 pom.xml。

POM 包含了關於工程和各類配置細節的信息,Maven 使用這些信息構建工程。

POM 也包含了目標和插件。當執行一個任務或者目標時,Maven 會查找當前目錄下的 POM,從其中讀取所須要的配置信息,而後執行目標。可以在 POM 中設置的一些配置以下:

  • project dependencies
  • plugins
  • goals
  • build profiles
  • project version
  • developers
  • mailing list

在建立 POM 以前,咱們首先肯定工程組(groupId),及其名稱(artifactId)和版本,在倉庫中這些屬性是工程的惟一標識。

POM 舉例

<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.companyname.project-group</groupId>    <artifactId>project</artifactId>    <version>1.0</version>  </project>

須要說明的是每一個工程應該只有一個 POM 文件。

  • 全部的 POM 文件須要 project 元素和三個必須的字段:groupId, artifactId,version。
  • 在倉庫中的工程標識爲 groupId:artifactId:version
  • POM.xml 的根元素是 project,它有三個主要的子節點:
節點
描述
groupId 這是工程組的標識。它在一個組織或者項目中一般是惟一的。例如,一個銀行組織 com.company.bank 擁有全部的和銀行相關的項目。
artifactId 這是工程的標識。它一般是工程的名稱。例如,消費者銀行。groupId 和 artifactId 一塊兒定義了 artifact 在倉庫中的位置。
version 這是工程的版本號。在 artifact 的倉庫中,它用來區分不一樣的版本。例如:
com.company.bank:consumer-banking:1.0
com.company.bank:consumer-banking:1.1.

Super POM

全部的 POM 都繼承自一個父 POM(不管是否顯式定義了這個父 POM)。父 POM 也被稱做 Super POM,它包含了一些能夠被繼承的默認設置。

Maven 使用 effective pom(Super pom 加上工程本身的配置)來執行相關的目標,它幫助開發者在 pom.xml 中作儘量少的配置,固然這些配置能夠被方便的重寫。

查看 Super POM 默認配置的一個簡單方法是執行如下命令:mvn help:effective-pom

在你的電腦上的任意目錄下建立一個 pom.xml 文件,使用上面提到的示例 pom 中的內容。

在下面的例子中,咱們在 C:\MVN\project 目錄中建立了一個 pom.xml 文件。

如今打開命令控制檯,到 pom.xml 所在的目錄下執行如下 mvn 命令。

C:\MVN\project>mvn help:effective-pom

Maven 將會開始處理並顯示 effective-pom。

[INFO] Scanning for projects... [INFO] Searching repository for plugin with prefix: 'help'. [INFO] ------------------------------------------------------------------------ [INFO] Building Unnamed - com.companyname.project-group:project-name:jar:1.0 [INFO]    task-segment: [help:effective-pom] (aggregator-style) [INFO] ------------------------------------------------------------------------ [INFO] [help:effective-pom {execution: default-cli}] [INFO]  .....  [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------------ [INFO] Total time: < 1 second [INFO] Finished at: Thu Jul 05 11:41:51 IST 2012 [INFO] Final Memory: 6M/15M [INFO] ------------------------------------------------------------------------

Effective POM 的結果就像在控制檯中顯示的同樣,通過繼承、插值以後,使配置生效。

<?xml version="1.0" encoding="UTF-8"?> <!-- ================================================================= --> <!--                                                                   --> <!-- Generated by Maven Help Plugin on 2012-07-05T11:41:51             --> <!-- See: http://maven.apache.org/plugins/maven-help-plugin/           --> <!--                                                                   --> <!-- ================================================================= -->  <!-- ================================================================= --> <!--                                                                   --> <!-- Effective POM for project                                         --> <!-- 'com.companyname.project-group:project-name:jar:1.0'              --> <!--                                                                   --> <!-- ================================================================= -->  <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 h ttp://maven.apache.org/xsd/maven-4.0.0.xsd">   <modelVersion>4.0.0</modelVersion>   <groupId>com.companyname.project-group</groupId>   <artifactId>project</artifactId>   <version>1.0</version>   <build>     <sourceDirectory>C:\MVN\project\src\main\java</sourceDirectory>     <scriptSourceDirectory>src/main/scripts</scriptSourceDirectory>     <testSourceDirectory>C:\MVN\project\src\test\java</testSourceDirectory>     <outputDirectory>C:\MVN\project\target\classes</outputDirectory>     <testOutputDirectory>C:\MVN\project\target\test-classes</testOutputDirectory>     <resources>       <resource>         <mergeId>resource-0</mergeId>         <directory>C:\MVN\project\src\main\resources</directory>       </resource>     </resources>     <testResources>       <testResource>         <mergeId>resource-1</mergeId>         <directory>C:\MVN\project\src\test\resources</directory>       </testResource>     </testResources>     <directory>C:\MVN\project\target</directory>     <finalName>project-1.0</finalName>     <pluginManagement>       <plugins>         <plugin>           <artifactId>maven-antrun-plugin</artifactId>           <version>1.3</version>         </plugin>         <plugin>           <artifactId>maven-assembly-plugin</artifactId>           <version>2.2-beta-2</version>         </plugin>         <plugin>           <artifactId>maven-clean-plugin</artifactId>           <version>2.2</version>         </plugin>         <plugin>           <artifactId>maven-compiler-plugin</artifactId>           <version>2.0.2</version>         </plugin>         <plugin>           <artifactId>maven-dependency-plugin</artifactId>           <version>2.0</version>         </plugin>         <plugin>           <artifactId>maven-deploy-plugin</artifactId>           <version>2.4</version>         </plugin>         <plugin>           <artifactId>maven-ear-plugin</artifactId>           <version>2.3.1</version>         </plugin>         <plugin>           <artifactId>maven-ejb-plugin</artifactId>           <version>2.1</version>         </plugin>         <plugin>           <artifactId>maven-install-plugin</artifactId>           <version>2.2</version>         </plugin>         <plugin>           <artifactId>maven-jar-plugin</artifactId>           <version>2.2</version>         </plugin>         <plugin>           <artifactId>maven-javadoc-plugin</artifactId>           <version>2.5</version>         </plugin>         <plugin>           <artifactId>maven-plugin-plugin</artifactId>           <version>2.4.3</version>         </plugin>         <plugin>           <artifactId>maven-rar-plugin</artifactId>           <version>2.2</version>         </plugin>         <plugin>           <artifactId>maven-release-plugin</artifactId>           <version>2.0-beta-8</version>         </plugin>         <plugin>           <artifactId>maven-resources-plugin</artifactId>           <version>2.3</version>         </plugin>         <plugin>           <artifactId>maven-site-plugin</artifactId>           <version>2.0-beta-7</version>         </plugin>         <plugin>           <artifactId>maven-source-plugin</artifactId>           <version>2.0.4</version>         </plugin>         <plugin>           <artifactId>maven-surefire-plugin</artifactId>           <version>2.4.3</version>         </plugin>         <plugin>           <artifactId>maven-war-plugin</artifactId>           <version>2.1-alpha-2</version>         </plugin>       </plugins>     </pluginManagement>     <plugins>       <plugin>         <artifactId>maven-help-plugin</artifactId>         <version>2.1.1</version>       </plugin>     </plugins>   </build>   <repositories>     <repository>       <snapshots>         <enabled>false</enabled>       </snapshots>       <id>central</id>       <name>Maven Repository Switchboard</name>       <url>http://repo1.maven.org/maven2</url>     </repository>   </repositories>   <pluginRepositories>     <pluginRepository>       <releases>         <updatePolicy>never</updatePolicy>       </releases>       <snapshots>         <enabled>false</enabled>       </snapshots>       <id>central</id>       <name>Maven Plugin Repository</name>       <url>http://repo1.maven.org/maven2</url>     </pluginRepository>   </pluginRepositories>   <reporting>     <outputDirectory>C:\MVN\project\target/site</outputDirectory>   </reporting> </project>

在上面的 pom.xml 中,你能夠看到 Maven 在執行目標時須要用到的默認工程源碼目錄結構、輸出目錄、須要的插件、倉庫和報表目錄。

Maven 的 pom.xml 文件也不須要手工編寫。

Maven 提供了大量的原型插件來建立工程,包括工程結構和 pom.xml。

詳細內容請參考 Maven - 插件 和 Maven - 建立工程 部分的內容。



 

Maven - 構建生命週期

 

什麼是構建生命週期

 

構建生命週期是一組階段的序列(sequence of phases),每一個階段定義了目標被執行的順序。這裏的階段是生命週期的一部分。

 

舉例說明,一個典型的 Maven 構建生命週期是由如下幾個階段的序列組成的:

 

階段
處理
描述
prepare-resources 資源拷貝 本階段能夠自定義須要拷貝的資源
compile 編譯 本階段完成源代碼編譯
package 打包 本階段根據 pom.xml 中描述的打包配置建立 JAR / WAR 包
install 安裝 本階段在本地 / 遠程倉庫中安裝工程包

 

當須要在某個特定階段以前或以後執行目標時,可使用 pre 和 post 來定義這個目標。

 

當 Maven 開始構建工程,會按照所定義的階段序列的順序執行每一個階段註冊的目標。Maven 有如下三個標準的生命週期:

 

  • clean
  • default(or build)
  • site

 

目標表示一個特定的、對構建和管理工程有幫助的任務。它可能綁定了 0 個或多個構建階段。沒有綁定任何構建階段的目標能夠在構建生命週期以外被直接調用執行。

 

執行的順序依賴於目標和構建階段被調用的順序。例如,考慮下面的命令。clean 和 package 參數是構建階段,而 dependency:copy-dependencies 是一個目標。

 

mvn clean dependency:copy-dependencies package

 

這裏的 clean 階段將會被首先執行,而後 dependency:copy-dependencies 目標會被執行,最終 package 階段被執行。

 

Clean 生命週期

 

當咱們執行 mvn post-clean 命令時,Maven 調用 clean 生命週期,它包含如下階段。

 

  • pre-clean
  • clean
  • post-clean

 

Maven 的 clean 目標(clean:clean)綁定到了 clean 生命週期的 clean 階段。它的 clean:clean 目標經過刪除構建目錄刪除了構建輸出。因此當 mvn clean 命令執行時,Maven 刪除了構建目錄。

 

咱們能夠經過在上面的 clean 生命週期的任何階段定義目標來修改這部分的操做行爲。

 

在下面的例子中,咱們將 maven-antrun-plugin:run 目標添加到 pre-clean、clean 和 post-clean 階段中。這樣咱們能夠在 clean 生命週期的各個階段顯示文本信息。

 

咱們已經在 C:\MVN\project 目錄下建立了一個 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.companyname.projectgroup</groupId> <artifactId>project</artifactId> <version>1.0</version> <build> <plugins>    <plugin>    <groupId>org.apache.maven.plugins</groupId>    <artifactId>maven-antrun-plugin</artifactId>    <version>1.1</version>    <executions>       <execution>          <id>id.pre-clean</id>          <phase>pre-clean</phase>          <goals>             <goal>run</goal>          </goals>          <configuration>             <tasks>                <echo>pre-clean phase</echo>             </tasks>          </configuration>       </execution>       <execution>          <id>id.clean</id>          <phase>clean</phase>          <goals>           <goal>run</goal>          </goals>          <configuration>             <tasks>                <echo>clean phase</echo>             </tasks>          </configuration>       </execution>       <execution>          <id>id.post-clean</id>          <phase>post-clean</phase>          <goals>             <goal>run</goal>          </goals>          <configuration>             <tasks>                <echo>post-clean phase</echo>             </tasks>          </configuration>       </execution>    </executions>    </plugin> </plugins> </build> </project>

 

如今打開命令控制檯,跳轉到 pom.xml 所在目錄,並執行下面的 mvn 命令。

 

C:\MVN\project>mvn post-clean

 

Maven 將會開始處理並顯示 clean 生命週期的全部階段。

 

[INFO] Scanning for projects... [INFO] ------------------------------------------------------------------ [INFO] Building Unnamed - com.companyname.projectgroup:project:jar:1.0 [INFO]    task-segment: [post-clean] [INFO] ------------------------------------------------------------------ [INFO] [antrun:run {execution: id.pre-clean}] [INFO] Executing tasks      [echo] pre-clean phase [INFO] Executed tasks [INFO] [clean:clean {execution: default-clean}] [INFO] [antrun:run {execution: id.clean}] [INFO] Executing tasks      [echo] clean phase [INFO] Executed tasks [INFO] [antrun:run {execution: id.post-clean}] [INFO] Executing tasks      [echo] post-clean phase [INFO] Executed tasks [INFO] ------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------ [INFO] Total time: < 1 second [INFO] Finished at: Sat Jul 07 13:38:59 IST 2012 [INFO] Final Memory: 4M/44M [INFO] ------------------------------------------------------------------

 

你能夠嘗試修改 mvn clean 命令,來顯示 pre-clean 和 clean,而在 post-clean 階段不執行任何操做。

 

Default (or Build) 生命週期

 

這是 Maven 的主要生命週期,被用於構建應用。包括下面的 23 個階段。

 

生命週期階段
描述
validate 檢查工程配置是否正確,完成構建過程的全部必要信息是否可以獲取到。
initialize 初始化構建狀態,例如設置屬性。
generate-sources 生成編譯階段須要包含的任何源碼文件。
process-sources 處理源代碼,例如,過濾任何值(filter any value)。
generate-resources 生成工程包中須要包含的資源文件。
process-resources 拷貝和處理資源文件到目的目錄中,爲打包階段作準備。
compile 編譯工程源碼。
process-classes 處理編譯生成的文件,例如 Java Class 字節碼的增強和優化。
generate-test-sources 生成編譯階段須要包含的任何測試源代碼。
process-test-sources 處理測試源代碼,例如,過濾任何值(filter any values)。
test-compile 編譯測試源代碼到測試目的目錄。
process-test-classes 處理測試代碼文件編譯後生成的文件。
test 使用適當的單元測試框架(例如JUnit)運行測試。
prepare-package 在真正打包以前,爲準備打包執行任何須要的操做。
package 獲取編譯後的代碼,並按照可發佈的格式進行打包,例如 JAR、WAR 或者 EAR 文件。
pre-integration-test 在集成測試執行以前,執行所需的操做。例如,設置所需的環境變量。
integration-test 處理和部署必須的工程包到集成測試可以運行的環境中。
post-integration-test 在集成測試被執行後執行必要的操做。例如,清理環境。
verify 運行檢查操做來驗證工程包是有效的,並知足質量要求。
install 安裝工程包到本地倉庫中,該倉庫能夠做爲本地其餘工程的依賴。
deploy 拷貝最終的工程包到遠程倉庫中,以共享給其餘開發人員和工程。

 

有一些與 Maven 生命週期相關的重要概念須要說明:

 

當一個階段經過 Maven 命令調用時,例如 mvn compile,只有該階段以前以及包括該階段在內的全部階段會被執行。

 

不一樣的 maven 目標將根據打包的類型(JAR / WAR / EAR),被綁定到不一樣的 Maven 生命週期階段。

 

在下面的例子中,咱們將 maven-antrun-plugin:run 目標添加到 Build 生命週期的一部分階段中。這樣咱們能夠顯示生命週期的文本信息。

 

咱們已經更新了 C:\MVN\project 目錄下的 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.companyname.projectgroup</groupId> <artifactId>project</artifactId> <version>1.0</version> <build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-antrun-plugin</artifactId> <version>1.1</version> <executions>    <execution>       <id>id.validate</id>       <phase>validate</phase>       <goals>          <goal>run</goal>       </goals>       <configuration>          <tasks>             <echo>validate phase</echo>          </tasks>       </configuration>    </execution>    <execution>       <id>id.compile</id>       <phase>compile</phase>       <goals>          <goal>run</goal>       </goals>       <configuration>          <tasks>             <echo>compile phase</echo>          </tasks>       </configuration>    </execution>    <execution>       <id>id.test</id>       <phase>test</phase>       <goals>          <goal>run</goal>       </goals>       <configuration>          <tasks>             <echo>test phase</echo>          </tasks>       </configuration>    </execution>    <execution>          <id>id.package</id>          <phase>package</phase>          <goals>             <goal>run</goal>          </goals>          <configuration>          <tasks>             <echo>package phase</echo>          </tasks>       </configuration>    </execution>    <execution>       <id>id.deploy</id>       <phase>deploy</phase>       <goals>          <goal>run</goal>       </goals>       <configuration>       <tasks>          <echo>deploy phase</echo>       </tasks>       </configuration>    </execution> </executions> </plugin> </plugins> </build> </project>

 

如今打開命令控制檯,跳轉到 pom.xml 所在目錄,並執行如下 mvn 命令。

 

C:\MVN\project>mvn compile

 

Maven 將會開始處理並顯示直到編譯階段的構建生命週期的各個階段。

 

[INFO] Scanning for projects... [INFO] ------------------------------------------------------------------ [INFO] Building Unnamed - com.companyname.projectgroup:project:jar:1.0 [INFO]    task-segment: [compile] [INFO] ------------------------------------------------------------------ [INFO] [antrun:run {execution: id.validate}] [INFO] Executing tasks      [echo] validate phase [INFO] Executed tasks [INFO] [resources:resources {execution: default-resources}] [WARNING] Using platform encoding (Cp1252 actually) to copy filtered resources, i.e. build is platform dependent! [INFO] skip non existing resourceDirectory C:\MVN\project\src\main\resources [INFO] [compiler:compile {execution: default-compile}] [INFO] Nothing to compile - all classes are up to date [INFO] [antrun:run {execution: id.compile}] [INFO] Executing tasks      [echo] compile phase [INFO] Executed tasks [INFO] ------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------ [INFO] Total time: 2 seconds [INFO] Finished at: Sat Jul 07 20:18:25 IST 2012 [INFO] Final Memory: 7M/64M [INFO] ------------------------------------------------------------------

 

Site 生命週期

 

Maven Site 插件通常用來建立新的報告文檔、部署站點等。

 

階段:

 

  • pre-site
  • site
  • post-site
  • site-deploy

 

在下面的例子中,咱們將 maven-antrun-plugin:run 目標添加到 Site 生命週期的全部階段中。這樣咱們能夠顯示生命週期的全部文本信息。

 

咱們已經更新了 C:\MVN\project 目錄下的 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.companyname.projectgroup</groupId> <artifactId>project</artifactId> <version>1.0</version> <build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-antrun-plugin</artifactId> <version>1.1</version>    <executions>       <execution>          <id>id.pre-site</id>          <phase>pre-site</phase>          <goals>             <goal>run</goal>          </goals>          <configuration>             <tasks>                <echo>pre-site phase</echo>             </tasks>          </configuration>       </execution>       <execution>          <id>id.site</id>          <phase>site</phase>          <goals>          <goal>run</goal>          </goals>          <configuration>             <tasks>                <echo>site phase</echo>             </tasks>          </configuration>       </execution>       <execution>          <id>id.post-site</id>          <phase>post-site</phase>          <goals>             <goal>run</goal>          </goals>          <configuration>             <tasks>                <echo>post-site phase</echo>             </tasks>          </configuration>       </execution>       <execution>          <id>id.site-deploy</id>          <phase>site-deploy</phase>          <goals>             <goal>run</goal>          </goals>          <configuration>             <tasks>                <echo>site-deploy phase</echo>             </tasks>          </configuration>       </execution>    </executions> </plugin> </plugins> </build> </project>

 

如今打開命令控制檯,跳轉到 pom.xml 所在目錄,並執行如下 mvn 命令。

 

C:\MVN\project>mvn site

 

Maven 將會開始處理並顯示直到 site 階段的 site 生命週期的各個階段。

 

[INFO] Scanning for projects... [INFO] ------------------------------------------------------------------ [INFO] Building Unnamed - com.companyname.projectgroup:project:jar:1.0 [INFO]    task-segment: [site] [INFO] ------------------------------------------------------------------ [INFO] [antrun:run {execution: id.pre-site}] [INFO] Executing tasks      [echo] pre-site phase [INFO] Executed tasks [INFO] [site:site {execution: default-site}] [INFO] Generating "About" report. [INFO] Generating "Issue Tracking" report. [INFO] Generating "Project Team" report. [INFO] Generating "Dependencies" report. [INFO] Generating "Project Plugins" report. [INFO] Generating "Continuous Integration" report. [INFO] Generating "Source Repository" report. [INFO] Generating "Project License" report. [INFO] Generating "Mailing Lists" report. [INFO] Generating "Plugin Management" report. [INFO] Generating "Project Summary" report. [INFO] [antrun:run {execution: id.site}] [INFO] Executing tasks      [echo] site phase [INFO] Executed tasks [INFO] ------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------ [INFO] Total time: 3 seconds [INFO] Finished at: Sat Jul 07 15:25:10 IST 2012 [INFO] Final Memory: 24M/149M [INFO] ------------------------------------------------------------------```



 

Maven - 構建配置文件

 

什麼是構建配置文件?

 

構建配置文件是一組配置的集合,用來設置或者覆蓋 Maven 構建的默認配置。使用構建配置文件,能夠爲不一樣的環境定製構建過程,例如 Producation 和 Development 環境。

 

Profile 在 pom.xml 中使用 activeProfiles / profiles 元素指定,而且能夠用不少方式觸發。Profile 在構建時修改 POM,而且爲變量設置不一樣的目標環境(例如,在開發、測試和產品環境中的數據庫服務器路徑)。

 

Profile 類型

 

Profile 主要有三種類型。

 

類型
在哪裏定義
Per Project 定義在工程 POM 文件 pom.xml 中
Per User 定義在 Maven 設置 xml 文件中 (%USER_HOME%/.m2/settings.xml)
Global 定義在 Maven 全局配置 xml 文件中 (%M2_HOME%/conf/settings.xml)

 

Profile 激活

 

Maven 的 Profile 可以經過幾種不一樣的方式激活。

 

  • 顯式使用命令控制檯輸入
  • 經過 maven 設置
  • 基於環境變量(用戶 / 系統變量)
  • 操做系統配置(例如,Windows family)
  • 現存 / 缺失 文件

 

Profile 激活示例

 

咱們假定你的工程目錄像下面這樣:

 

Maven Build Profile

 

如今,在 src/main/resources 目錄下有三個環境配置文件:

 

文件名稱
描述
env.properties 沒有配置文件時的默認配置
env.test.properties 使用測試配置文件時的測試配置
env.prod.properties 使用產品配置文件時的產品配置

 

顯式 Profile 激活

 

在接下來的例子中,咱們將 attach maven-antrun-plugin:run 目標添加到測試階段中。這樣能夠咱們在不一樣的 Profile 中輸出文本信息。咱們將使用 pom.xml 來定義不一樣的 Profile,並在命令控制檯中使用 maven 命令激活 Profile。

 

假定,咱們在 C:\MVN\project 目錄下建立了如下的 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.companyname.projectgroup</groupId>    <artifactId>project</artifactId>    <version>1.0</version>    <profiles>       <profile>       <id>test</id>       <build>       <plugins>          <plugin>             <groupId>org.apache.maven.plugins</groupId>             <artifactId>maven-antrun-plugin</artifactId>             <version>1.1</version>             <executions>                <execution>                   <phase>test</phase>                   <goals>                      <goal>run</goal>                   </goals>                   <configuration>                   <tasks>                      <echo>Using env.test.properties</echo>             <copy file="src/main/resources/env.test.propertiestofile             ="${project.build.outputDirectory}/env.properties"/>                   </tasks>                   </configuration>                </execution>             </executions>          </plugin>       </plugins>       </build>       </profile>    </profiles> </project>

 

如今打開命令控制檯,跳轉到 pom.xml 所在目錄,並執行如下 mvn 命令。使用 -P 選項指定 Profile 的名稱。

 

C:\MVN\project>mvn test -Ptest

 

Maven 將開始處理並顯示 test Profile 的結果。

 

[INFO] Scanning for projects... [INFO] ------------------------------------------------------------------ [INFO] Building Unnamed - com.companyname.projectgroup:project:jar:1.0 [INFO]    task-segment: [test] [INFO] ------------------------------------------------------------------ [INFO] [resources:resources {execution: default-resources}] [WARNING] Using platform encoding (Cp1252 actually) to copy filtered resources, i.e. build is platform dependent! [INFO] Copying 3 resources [INFO] [compiler:compile {execution: default-compile}] [INFO] Nothing to compile - all classes are up to date [INFO] [resources:testResources {execution: default-testResources}] [WARNING] Using platform encoding (Cp1252 actually) to copy filtered resources, i.e. build is platform dependent! [INFO] skip non existing resourceDirectory C:\MVN\project\src\test\resources [INFO] [compiler:testCompile {execution: default-testCompile}] [INFO] Nothing to compile - all classes are up to date [INFO] [surefire:test {execution: default-test}] [INFO] Surefire report directory: C:\MVN\project\target\surefire-reports  -------------------------------------------------------  T E S T S ------------------------------------------------------- There are no tests to run.  Results :  Tests run: 0, Failures: 0, Errors: 0, Skipped: 0  [INFO] [antrun:run {execution: default}] [INFO] Executing tasks      [echo] Using env.test.properties [INFO] Executed tasks [INFO] ------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------ [INFO] Total time: 1 second [INFO] Finished at: Sun Jul 08 14:55:41 IST 2012 [INFO] Final Memory: 8M/64M [INFO] ------------------------------------------------------------------

 

如今咱們練習一下,你能夠按照下面的步驟作:

 

  • 在 pom.xml 的 profiles 元素中添加另外一個 profile 元素(拷貝已有的 profile 元素並粘貼到 profiles 元素結尾)。
  • 將此 profile 元素的 id 從 test 修改成 normal。
  • 將任務部分修改成 echo env.properties,以及 copy env.properties 到目標目錄
  • 再次重複以上三個步驟,修改 id 爲 prod,修改 task 部分爲 env.prod.properties
  • 所有就這些了。如今你有了三個構建配置文件(normal / test / prod)。

 

如今打開命令控制檯,跳轉到 pom.xml 所在目錄,並執行下面的 mvn 命令。使用 -P 選項指定 Profile 的名稱。

 

C:\MVN\project>mvn test -Pnormal C:\MVN\project>mvn test -Pprod

 

檢查構建的輸出看看有什麼不一樣。

 

經過 Maven 設置激活 Profile

 

打開 Maven 的 settings.xml 文件,該文件能夠在 %USER_HOME%/.m2 目錄下找到,%USER_HOME% 表示用戶主目錄。若是 settings.xml 文件不存在則須要建立一個。

 

像在下面例子中展現的同樣,使用 activeProfiles 節點添加 test 配置做爲激活的 Profile。

 

<settings 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/settings-1.0.0.xsd">    <mirrors>       <mirror>          <id>maven.dev.snaponglobal.com</id>          <name>Internal Artifactory Maven repository</name>          <url>http://repo1.maven.org/maven2/</url>          <mirrorOf>*</mirrorOf>       </mirror>    </mirrors>    <activeProfiles>       <activeProfile>test</activeProfile>    </activeProfiles> </settings>

 

如今打開命令控制檯,跳轉到 pom.xml 所在目錄,並執行下面的 mvn 命令。不要使用 -P 選項指定 Profile 的名稱。Maven 將顯示被激活的 test Profile 的結果。

 

C:\MVN\project>mvn test

 

經過環境變量激活 Profile

 

如今從 maven 的 settings.xml 中刪除激活的 Profile,並更新 pom.xml 中的 test Profile。將下面的內容添加到 profile 元素的 activation 元素中。

 

當系統屬性 「env」 被設置爲 「test」 時,test 配置將會被觸發。建立一個環境變量 「env」 並設置它的值爲 「test」。

 

<profile>    <id>test</id>    <activation>       <property>          <name>env</name>          <value>test</value>       </property>    </activation> </profile>

 

如今打開命令控制檯,跳轉到 pom.xml 所在目錄,並執行下面的 mvn 命令。

 

C:\MVN\project>mvn test

 

經過操做系統激活 Profile

 

activation 元素包含下面的操做系統信息。當系統爲 windows XP 時,test Profile 將會被觸發。

 

<profile>    <id>test</id>    <activation>       <os>          <name>Windows XP</name>          <family>Windows</family>          <arch>x86</arch>          <version>5.1.2600</version>       </os>    </activation> </profile>

 

如今打開命令控制檯,跳轉到 pom.xml 所在目錄,並執行下面的 mvn 命令。不要使用 -P 選項指定 Profile 的名稱。Maven 將顯示被激活的 test Profile 的結果。

 

C:\MVN\project>mvn test

 

經過現存 / 缺失的文件激活 Profile

 

如今使用 activation 元素包含下面的操做系統信息。當 target/generated-sources/axistools/wsdl2java/com/companyname/group 缺失時,test Profile 將會被觸發。

 

<profile>    <id>test</id>    <activation>       <file>          <missing>target/generated-sources/axistools/wsdl2java/          com/companyname/group</missing>       </file>    </activation> </profile>

 

如今打開命令控制檯,跳轉到 pom.xml 所在目錄,並執行下面的 mvn 命令。不要使用 -P 選項指定 Profile 的名稱。Maven 將顯示被激活的 test Profile 的結果。

 

C:\MVN\project>mvn test

Maven - 倉庫

什麼是 Maven 倉庫?

在 Maven 的術語中,倉庫是一個位置(place),例如目錄,能夠存儲全部的工程 jar 文件、library jar 文件、插件或任何其餘的工程指定的文件。

Maven 倉庫有三種類型:

  • 本地(local)
  • 中央(central)
  • 遠程(remote)

本地倉庫

Maven 本地倉庫是機器上的一個文件夾。它在你第一次運行任何 maven 命令的時候建立。

Maven 本地倉庫保存你的工程的全部依賴(library jar、plugin jar 等)。當你運行一次 Maven 構建,Maven 會自動下載全部依賴的 jar 文件到本地倉庫中。它避免了每次構建時都引用存放在遠程機器上的依賴文件。

Maven 本地倉庫默認被建立在 %USER_HOME% 目錄下。要修改默認位置,在 %M2_HOME%\conf 目錄中的 Maven 的 settings.xml 文件中定義另外一個路徑。

<settings xmlns="http://maven.apache.org/SETTINGS/1.0.0"    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"    xsi:schemaLocation="http://maven.apache.org/SETTINGS/1.0.0     http://maven.apache.org/xsd/settings-1.0.0.xsd">       <localRepository>C:/MyLocalRepository</localRepository> </settings>

當你運行 Maven 命令,Maven 將下載依賴的文件到你指定的路徑中。

中央倉庫

Maven 中央倉庫是由 Maven 社區提供的倉庫,其中包含了大量經常使用的庫。

中央倉庫的關鍵概念:

  • 這個倉庫由 Maven 社區管理。
  • 不須要配置。
  • 須要經過網絡才能訪問。

要瀏覽中央倉庫的內容,maven 社區提供了一個 URL: http://search.maven.org/#browse。使用這個倉庫,開發人員能夠搜索全部能夠獲取的代碼庫。

遠程倉庫

若是 Maven 在中央倉庫中也找不到依賴的庫文件,它會中止構建過程並輸出錯誤信息到控制檯。爲避免這種狀況,Maven 提供了遠程倉庫的概念,它是開發人員本身定製倉庫,包含了所須要的代碼庫或者其餘工程中用到的 jar 文件。

舉例說明,使用下面的 POM.xml,Maven 將從遠程倉庫中下載該 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.companyname.projectgroup</groupId>    <artifactId>project</artifactId>    <version>1.0</version>    <dependencies>       <dependency>          <groupId>com.companyname.common-lib</groupId>          <artifactId>common-lib</artifactId>          <version>1.0.0</version>       </dependency>    <dependencies>    <repositories>       <repository>          <id>companyname.lib1</id>          <url>http://download.companyname.org/maven2/lib1</url>       </repository>       <repository>          <id>companyname.lib2</id>          <url>http://download.companyname.org/maven2/lib2</url>       </repository>    </repositories> </project>

Maven 依賴搜索順序

當咱們執行 Maven 構建命令時,Maven 開始按照如下順序查找依賴的庫:

  • 步驟 1 - 在本地倉庫中搜索,若是找不到,執行步驟 2,若是找到了則執行其餘操做。
  • 步驟 2 - 在中央倉庫中搜索,若是找不到,而且有一個或多個遠程倉庫已經設置,則執行步驟 4,若是找到了則下載到本地倉庫中已被未來引用。
  • 步驟 3 - 若是遠程倉庫沒有被設置,Maven 將簡單的停滯處理並拋出錯誤(沒法找到依賴的文件)。
  • 步驟 4 - 在一個或多個遠程倉庫中搜索依賴的文件,若是找到則下載到本地倉庫已被未來引用,不然 Maven 將中止處理並拋出錯誤(沒法找到依賴的文件)。

 

Maven - 插件

什麼是 Maven 插件?

Maven 其實是一個依賴插件執行的框架,每一個任務其實是由插件完成。Maven 插件一般被用來:

  • 建立 jar 文件
  • 建立 war 文件
  • 編譯代碼文件
  • 代碼單元測試
  • 建立工程文檔
  • 建立工程報告

插件一般提供了一個目標的集合,而且可使用下面的語法執行:

mvn [plugin-name]:[goal-name]

例如,一個 Java 工程可使用 maven-compiler-plugin 的 compile-goal 編譯,使用如下命令:

mvn compiler:compile

插件類型

Maven 提供了下面兩種類型的插件:

類型
描述
Build plugins 在構建時執行,並在 pom.xml 的 元素中配置。
Reporting plugins 在網站生成過程當中執行,並在 pom.xml 的 元素中配置。

下面是一些經常使用插件的列表:

插件
描述
clean 構建以後清理目標文件。刪除目標目錄。
compiler 編譯 Java 源文件。
surefile 運行 JUnit 單元測試。建立測試報告。
jar 從當前工程中構建 JAR 文件。
war 從當前工程中構建 WAR 文件。
javadoc 爲工程生成 Javadoc。
antrun 從構建過程的任意一個階段中運行一個 ant 任務的集合。

例子

咱們已經在咱們的例子中大量使用了 maven-antrun-plugin 來輸出數據到控制檯上。請查看 Maven - 構建配置文件 章節。讓咱們用一種更好的方式理解這部份內容,在 C:\MVN\project 目錄下建立一個 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.companyname.projectgroup</groupId> <artifactId>project</artifactId> <version>1.0</version> <build> <plugins>    <plugin>    <groupId>org.apache.maven.plugins</groupId>    <artifactId>maven-antrun-plugin</artifactId>    <version>1.1</version>    <executions>       <execution>          <id>id.clean</id>          <phase>clean</phase>          <goals>             <goal>run</goal>          </goals>          <configuration>             <tasks>                <echo>clean phase</echo>             </tasks>          </configuration>       </execution>         </executions>    </plugin> </plugins> </build> </project>

接下來,打開命令終端跳轉到 pom.xml 所在的目錄,並執行下面的 mvn 命令。

C:\MVN\project>mvn clean

Maven 將開始處理並顯示 clean 生命週期的 clean 階段。

[INFO] Scanning for projects... [INFO] ------------------------------------------------------------------ [INFO] Building Unnamed - com.companyname.projectgroup:project:jar:1.0 [INFO]    task-segment: [post-clean] [INFO] ------------------------------------------------------------------ [INFO] [clean:clean {execution: default-clean}] [INFO] [antrun:run {execution: id.clean}] [INFO] Executing tasks      [echo] clean phase [INFO] Executed tasks [INFO] ------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------ [INFO] Total time: < 1 second [INFO] Finished at: Sat Jul 07 13:38:59 IST 2012 [INFO] Final Memory: 4M/44M [INFO] ------------------------------------------------------------------

上面的例子展現瞭如下關鍵概念:

  • 插件是在 pom.xml 中使用 plugins 元素定義的。
  • 每一個插件能夠有多個目標。
  • 你能夠定義階段,插件會使用它的 phase 元素開始處理。咱們已經使用了 clean 階段。
  • 你能夠經過綁定到插件的目標的方式來配置要執行的任務。咱們已經綁定了 echo 任務到 maven-antrun-plugin 的 run 目標。
  • 就是這樣,Maven 將處理剩下的事情。它將下載本地倉庫中獲取不到的插件,並開始處理。

 

Maven - 建立工程

Maven 使用原型(archetype)插件建立工程。要建立一個簡單的 Java 應用,咱們將使用 maven-archetype-quickstart 插件。在下面的例子中,咱們將在 C:\MVN 文件夾下建立一個基於 maven 的 java 應用工程。

咱們打開命令控制檯,跳轉到 C:\MVN 目錄,並執行下面的 mvn 命令。

C:\MVN>mvn archetype:generate -DgroupId=com.companyname.bank  -DartifactId=consumerBanking  -DarchetypeArtifactId=maven-archetype-quickstart  -DinteractiveMode=false

Maven 將開始處理,並將建立完成的 java 應用工程結構。

INFO] Scanning for projects... [INFO] Searching repository for plugin with prefix: 'archetype'. [INFO] ------------------------------------------------------------------- [INFO] Building Maven Default Project [INFO]    task-segment: [archetype:generate] (aggregator-style) [INFO] ------------------------------------------------------------------- [INFO] Preparing archetype:generate [INFO] No goals needed for project - skipping [INFO] [archetype:generate {execution: default-cli}] [INFO] Generating project in Batch mode [INFO] ------------------------------------------------------------------- [INFO] Using following parameters for creating project   from Old (1.x) Archetype: maven-archetype-quickstart:1.0 [INFO] ------------------------------------------------------------------- [INFO] Parameter: groupId, Value: com.companyname.bank [INFO] Parameter: packageName, Value: com.companyname.bank [INFO] Parameter: package, Value: com.companyname.bank [INFO] Parameter: artifactId, Value: consumerBanking [INFO] Parameter: basedir, Value: C:\MVN [INFO] Parameter: version, Value: 1.0-SNAPSHOT [INFO] project created from Old (1.x) Archetype in dir: C:\MVN\consumerBanking [INFO] ------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------ [INFO] Total time: 14 seconds [INFO] Finished at: Tue Jul 10 15:38:58 IST 2012 [INFO] Final Memory: 21M/124M [INFO] ------------------------------------------------------------------

如今跳轉到 C:/MVN 目錄。有將看到一個名爲 consumerBanking 的 java 應用工程(就像在 artifactId 中設定的同樣)。Maven 使用一套標準的目錄結構,就像這樣:

Java application project structure

使用上面的例子,咱們能夠知道下面幾個關鍵概念:

文件夾結構
描述
consumerBanking 包含 src 文件夾和 pom.xml
src/main/java contains java 代碼文件在包結構下(com/companyName/bank)。
src/main/test contains 測試代碼文件在包結構下(com/companyName/bank)。
src/main/resources 包含了 圖片 / 屬性 文件(在上面的例子中,咱們須要手動建立這個結構)。

Maven 也建立了一個簡單的 Java 源文件和 Java 測試文件。打開 C:\MVN\consumerBanking\src\main\java\com\companyname\bank 文件夾,能夠看到 App.java 文件。

package com.companyname.bank;  /**  * Hello world!  *  */ public class App  {     public static void main( String[] args )     {         System.out.println( "Hello World!" );     } }

打開 C:\MVN\consumerBanking\src\test\java\com\companyname\bank 文件夾,能夠看到 AppTest.java。

package com.companyname.bank;  import junit.framework.Test; import junit.framework.TestCase; import junit.framework.TestSuite;  /**  * Unit test for simple App.  */ public class AppTest extends TestCase  {     /**      * Create the test case      *      * @param testName name of the test case      */     public AppTest( String testName )     {         super( testName );     }      /**      * @return the suite of tests being tested      */     public static Test suite()     {         return new TestSuite( AppTest.class );     }      /**      * Rigourous Test :-)      */     public void testApp()     {         assertTrue( true );     } }

開發人員須要將他們的文件按照上面表格中提到的結構放置好,接下來 Maven 將會搞定全部構建相關的複雜任務。

在下個章節中,咱們將討論如何使用 maven 構建和測試工程:Maven - 構建 & 測試工程

 

 

Maven - 構建 & 測試工程

咱們在建立工程章節中學到的是如何使用 Maven 建立 Java 應用。如今咱們將看到如何構建和測試這個應用。

跳轉到 C:/MVN 目錄下,既你的 java 應用目錄下。打開 consumerBanking 文件夾。你將看到 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.companyname.projectgroup</groupId>       <artifactId>project</artifactId>       <version>1.0</version>       <dependencies>          <dependency>             <groupId>junit</groupId>             <artifactId>junit</artifactId>             <version>3.8.1</version>          </dependency>       </dependencies>   </project>

能夠看到,Maven 已經添加了 JUnit 做爲測試框架。默認 Maven 添加了一個源碼文件 App.java 和一個測試文件AppTest.java 到上個章節中咱們提到的默認目錄結構中。

打開命令控制檯,跳轉到 C:\MVN\consumerBanking 目錄下,並執行如下 mvn 命令。

C:\MVN\consumerBanking>mvn clean package

Maven 將開始構建工程。

[INFO] Scanning for projects... [INFO] ------------------------------------------------------------------- [INFO] Building consumerBanking [INFO]    task-segment: [clean, package] [INFO] ------------------------------------------------------------------- [INFO] [clean:clean {execution: default-clean}] [INFO] Deleting directory C:\MVN\consumerBanking\target [INFO] [resources:resources {execution: default-resources}] [WARNING] Using platform encoding (Cp1252 actually) to copy filtered resources, i.e. build is platform dependent! [INFO] skip non existing resourceDirectory C:\MVN\consumerBanking\src\main\ resources [INFO] [compiler:compile {execution: default-compile}] [INFO] Compiling 1 source file to C:\MVN\consumerBanking\target\classes [INFO] [resources:testResources {execution: default-testResources}] [WARNING] Using platform encoding (Cp1252 actually) to copy filtered resources, i.e. build is platform dependent! [INFO] skip non existing resourceDirectory C:\MVN\consumerBanking\src\test\ resources [INFO] [compiler:testCompile {execution: default-testCompile}] [INFO] Compiling 1 source file to C:\MVN\consumerBanking\target\test-classes [INFO] [surefire:test {execution: default-test}] [INFO] Surefire report directory: C:\MVN\consumerBanking\target\ surefire-reports -------------------------------------------------------  T E S T S ------------------------------------------------------- Running com.companyname.bank.AppTest Tests run: 1, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.027 sec  Results :  Tests run: 1, Failures: 0, Errors: 0, Skipped: 0  [INFO] [jar:jar {execution: default-jar}] [INFO] Building jar: C:\MVN\consumerBanking\target\ consumerBanking-1.0-SNAPSHOT.jar [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------------ [INFO] Total time: 2 seconds [INFO] Finished at: Tue Jul 10 16:52:18 IST 2012 [INFO] Final Memory: 16M/89M [INFO] ------------------------------------------------------------------------

你已經構建了你的工程並建立了最終的 jar 文件,下面是要學習的關鍵概念:

  • 咱們給了 maven 兩個目標,首先清理目標目錄(clean),而後打包工程構建的輸出爲 jar(package)文件。
  • 打包好的 jar 文件能夠在 consumerBanking\target 中得到,名稱爲 consumerBanking-1.0-SNAPSHOT.jar。
  • 測試報告存放在 consumerBanking\target\surefire-reports 文件夾中。
  • Maven 編譯源碼文件,以及測試源碼文件。
  • 接着 Maven 運行測試用例。
  • 最後 Maven 建立工程包。

如今打開命令控制檯,跳轉到 C:\MVN\consumerBanking\target\classes 目錄,並執行下面的 java 命令。

C:\MVN\consumerBanking\target\classes>java com.companyname.bank.App

你能夠看到結果:

Hello World!

添加 Java 源文件

咱們看看如何添加其餘的 Java 文件到工程中。打開 C:\MVN\consumerBanking\src\main\java\com\companyname\bank 文件夾,在其中建立 Util 類 Util.java。

package com.companyname.bank;  public class Util  {    public static void printMessage(String message){        System.out.println(message);    } }

更新 App 類來使用 Util 類。

package com.companyname.bank;  /**  * Hello world!  *  */ public class App  {     public static void main( String[] args )     {         Util.printMessage("Hello World!");     } }

如今打開命令控制檯,跳轉到 C:\MVN\consumerBanking 目錄下,並執行下面的 mvn 命令。

C:\MVN\consumerBanking>mvn clean compile

在 Maven 構建成功以後,跳轉到 C:\MVN\consumerBanking\target\classes 目錄下,並執行下面的 java 命令。

C:\MVN\consumerBanking\target\classes>java -cp com.companyname.bank.App

你能夠看到結果:

Hello World!

Maven - 外部依賴

如今,如你所知道的,Maven的依賴管理使用的是 Maven - 倉庫 的概念。可是若是在遠程倉庫和中央倉庫中,依賴不能被知足,如何解決呢? Maven 使用外部依賴的概念來解決這個問題。

例如,讓咱們對在 Maven - 建立工程 部分建立的項目作如下修改:

  • 在 src 文件夾下添加 lib 文件夾
  • 複製任何 jar 文件到 lib 文件夾下。咱們使用的是 ldapjdk.jar ,它是爲 LDAP 操做的一個幫助庫

如今,咱們的工程結構應該像下圖同樣:

external-project-structure

如今你有了本身的工程庫(library),一般狀況下它會包含一些任何倉庫沒法使用,而且 maven 也沒法下載的 jar 文件。若是你的代碼正在使用這個庫,那麼 Maven 的構建過程將會失敗,由於在編譯階段它不能下載或者引用這個庫。

爲了處理這種狀況,讓咱們用如下方式,將這個外部依賴添加到 maven 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/maven-v4_0_0.xsd">        <modelVersion>4.0.0</modelVersion>        <groupId>com.companyname.bank</groupId>        <artifactId>consumerBanking</artifactId>        <packaging>jar</packaging>        <version>1.0-SNAPSHOT</version>        <name>consumerBanking</name>        <url>http://maven.apache.org</url>         <dependencies>           <dependency>              <groupId>junit</groupId>              <artifactId>junit</artifactId>              <version>3.8.1</version>              <scope>test</scope>           </dependency>            <dependency>              <groupId>ldapjdk</groupId>              <artifactId>ldapjdk</artifactId>              <scope>system</scope>              <version>1.0</version>              <systemPath>${basedir}\src\lib\ldapjdk.jar</systemPath>           </dependency>        </dependencies>      </project>

上例中, <dependencies> 的第二個 <dependency> 元素 , 闡明瞭外部依賴的關鍵概念。

  • 外部依賴(library jar location)可以像其餘依賴同樣在 pom.xml 中配置。
  • 指定 groupId 爲 library 的名稱。
  • 指定 artifactId 爲 library 的名稱。
  • 指定做用域(scope)爲系統。
  • 指定相對於工程位置的系統路徑。

但願如今你懂得了有關外部依賴的知識,你將可以在你的 Maven 工程中指定外部依賴。

 

Maven - 工程文檔

本教程將教你如何建立應用程序的文檔。那麼讓咱們開始吧,在 C:/ MVN 目錄下,建立你的 javaconsumerBanking 應用程序。打開 consumerBanking 文件夾並執行如下 mvn 命令。

C:\MVN>mvn site

Maven 將開始構建工程。

[INFO] Scanning for projects... [INFO] ------------------------------------------------------------------- [INFO] Building consumerBanking [INFO]task-segment: [site] [INFO] ------------------------------------------------------------------- [INFO] [site:site {execution: default-site}] [INFO] artifact org.apache.maven.skins:maven-default-skin:  checking for updates from central [INFO] Generating "About" report. [INFO] Generating "Issue Tracking" report. [INFO] Generating "Project Team" report. [INFO] Generating "Dependencies" report. [INFO] Generating "Continuous Integration" report. [INFO] Generating "Source Repository" report. [INFO] Generating "Project License" report. [INFO] Generating "Mailing Lists" report. [INFO] Generating "Plugin Management" report. [INFO] Generating "Project Summary" report. [INFO] ------------------------------------------------------------------- [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------- [INFO] Total time: 16 seconds [INFO] Finished at: Wed Jul 11 18:11:18 IST 2012 [INFO] Final Memory: 23M/148M [INFO] -------------------------------------------------------------------

打開 C:\MVN\consumerBanking\target\site 文件夾。點擊 index.html 就能夠看到文檔了。

Maven 使用稱做 Doxia 的文件處理引擎建立文檔,它將多個源格式的文件轉換爲一個共通的文檔模型。要編寫工程文檔,你可使用如下可以被 Doxia 解析的幾種經常使用格式來編寫。

格式名稱
描述
引用
XDoc Maven 1.x 版本的文檔格式 http://jakarta.apache.org/site/jakarta-site2.html
FML FAQ 文檔格式 http://maven.apache.org/doxia/references/fml-format.html
XHTML 可擴展 HTML 格式 http://en.wikipedia.org/wiki/XHTML

 

 

Maven - 工程模板

Maven 使用原型(Archetype)概念爲用戶提供了大量不一樣類型的工程模版(614 個)。Maven 使用下面的命令幫助用戶快速建立 java 項目。

mvn archetype:generate

什麼是原型?

原型是一個 Maven 插件,它的任務是根據模板建立一個項目結構。咱們將使用 quickstart 原型插件建立一個簡單的 java 應用程序。

使用工程模板

讓咱們打開命令控制檯,跳轉到 C:\ > MVN 目錄並執行如下 mvn 命令

C:\MVN>mvn archetype:generate

Maven 將開始處理,並要求選擇所需的原型

INFO] Scanning for projects... [INFO] Searching repository for plugin with prefix: 'archetype'. [INFO] ------------------------------------------------------------------- [INFO] Building Maven Default Project [INFO]task-segment: [archetype:generate] (aggregator-style) [INFO] ------------------------------------------------------------------- [INFO] Preparing archetype:generate ... 600: remote -> org.trailsframework:trails-archetype (-) 601: remote -> org.trailsframework:trails-secure-archetype (-) 602: remote -> org.tynamo:tynamo-archetype (-) 603: remote -> org.wicketstuff.scala:wicket-scala-archetype (-) 604: remote -> org.wicketstuff.scala:wicketstuff-scala-archetype  Basic setup for a project that combines Scala and Wicket, depending on the Wicket-Scala project.  Includes an example Specs test.) 605: remote -> org.wikbook:wikbook.archetype (-) 606: remote -> org.xaloon.archetype:xaloon-archetype-wicket-jpa-glassfish (-) 607: remote -> org.xaloon.archetype:xaloon-archetype-wicket-jpa-spring (-) 608: remote -> org.xwiki.commons:xwiki-commons-component-archetype  (Make it easy to create a maven project for creating XWiki Components.) 609: remote -> org.xwiki.rendering:xwiki-rendering-archetype-macro  (Make it easy to create a maven project for creating XWiki Rendering Macros.) 610: remote -> org.zkoss:zk-archetype-component (The ZK Component archetype) 611: remote -> org.zkoss:zk-archetype-webapp (The ZK wepapp archetype) 612: remote -> ru.circumflex:circumflex-archetype (-) 613: remote -> se.vgregion.javg.maven.archetypes:javg-minimal-archetype (-) 614: remote -> sk.seges.sesam:sesam-annotation-archetype (-) Choose a number or apply filter  (format: [groupId:]artifactId, case sensitive contains): 203:

按下 Enter 選擇默認選項 (203:maven-archetype-quickstart)

Maven 將詢問原型的版本

Choose org.apache.maven.archetypes:maven-archetype-quickstart version: 1: 1.0-alpha-1 2: 1.0-alpha-2 3: 1.0-alpha-3 4: 1.0-alpha-4 5: 1.0 6: 1.1 Choose a number: 6:

按下 Enter 選擇默認選項 (6:maven-archetype-quickstart:1.1)

Maven 將詢問工程細節。按要求輸入工程細節。若是要使用默認值則直接按 Enter 鍵。你也能夠輸入本身的值。

Define value for property 'groupId': : com.companyname.insurance Define value for property 'artifactId': : health Define value for property 'version': 1.0-SNAPSHOT: Define value for property 'package': com.companyname.insurance:

Maven 將要求確認工程細節。按 enter 或按 Y

Confirm properties configuration: groupId: com.companyname.insurance artifactId: health version: 1.0-SNAPSHOT package: com.companyname.insurance Y:

如今 Maven 將開始建立工程結構,顯示以下:

[INFO] ----------------------------------------------------------------------- [INFO] Using following parameters for creating project  from Old (1.x) Archetype: maven-archetype-quickstart:1.1 [INFO] ----------------------------------------------------------------------- [INFO] Parameter: groupId, Value: com.companyname.insurance [INFO] Parameter: packageName, Value: com.companyname.insurance [INFO] Parameter: package, Value: com.companyname.insurance [INFO] Parameter: artifactId, Value: health [INFO] Parameter: basedir, Value: C:\MVN [INFO] Parameter: version, Value: 1.0-SNAPSHOT [INFO] project created from Old (1.x) Archetype in dir: C:\MVN\health [INFO] ----------------------------------------------------------------------- [INFO] BUILD SUCCESSFUL [INFO] ----------------------------------------------------------------------- [INFO] Total time: 4 minutes 12 seconds [INFO] Finished at: Fri Jul 13 11:10:12 IST 2012 [INFO] Final Memory: 20M/90M [INFO] -----------------------------------------------------------------------

建立的項目

如今轉到 C:\ > MVN 目錄。你會看到一個名爲 health 的 java 應用程序項目,就像在項目建立的時候創建的 artifactId 名稱同樣。 Maven 將建立一個有標準目錄佈局的工程,以下所示:

建立 POM.xml

Maven 爲工程生成一個 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.companyname.insurance</groupId>   <artifactId>health</artifactId>   <version>1.0-SNAPSHOT</version>   <packaging>jar</packaging>   <name>health</name>   <url>http://maven.apache.org</url>   <properties>      <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>   </properties>   <dependencies>      <dependency>      <groupId>junit</groupId>         <artifactId>junit</artifactId>         <version>3.8.1</version>         <scope>test</scope>      </dependency>   </dependencies> </project>

建立 App.java

Maven 生成一個 java 源文件示例,工程的 App.java 以下所示:

路徑:C:\ > MVN > health > src > main > java > com > companyname > insurance > App.java

package com.companyname.insurance;  /** * Hello world! * */ public class App  {     public static void main( String[] args )     {         System.out.println( "Hello World!" );     } }

建立 AppTest.java

Maven 生成一個 java 源文件示例,工程的 AppTest.java 以下所示:

路徑爲: C:\ > MVN > health > src > test > java > com > companyname > insurance > AppTest.java

package com.companyname.insurance;  import junit.framework.Test; import junit.framework.TestCase; import junit.framework.TestSuite;  /** * Unit test for simple App. */ public class AppTest     extends TestCase {    /**    * Create the test case    *    * @param testName name of the test case    */   public AppTest( String testName )   {       super( testName );   }    /**   * @return the suite of tests being tested   */   public static Test suite()   {       return new TestSuite( AppTest.class );   }    /**   * Rigourous Test :-)   */   public void testApp()   {       assertTrue( true );   } }

就這樣。如今你能夠看到 Maven 的強大之處。你能夠用 maven 簡單的命令建立任何類型的工程,而且能夠啓動您的開發。

 

Maven - 快照

大型軟件應用程序一般由多個模塊組成,這是多個團隊工做於同一應用程序的不一樣模塊的常見場景。例如一個團隊工做負責應用程序的前端應用用戶接口工程(app-ui.jar:1.0)),同時他們使用數據服務工程(data-service.jar:1.0)。

如今負責數據服務的團隊可能正在進行修正 bug 或者加強功能,並快速迭代,而後他們幾乎天天都會 release 工程庫文件到遠程倉庫中。

如今若是數據服務團隊天天上傳新的版本,那麼就會有下面的問題:

  • 每次數據服務團隊發佈了一版更新的代碼時,都要告訴應用接口團隊。
  • 應用接口團隊須要按期更新他們的 pom.xml 來獲得更新的版本

爲了解決這樣的狀況,快照概念發揮了做用.

什麼是快照?

快照是一個特殊的版本,它表示當前開發的一個副本。與常規版本不一樣,Maven 爲每一次構建從遠程倉庫中檢出一份新的快照版本。

如今數據服務團隊會將每次更新的代碼的快照(例如 data-service:1.0-SNAPSHOT)發佈到倉庫中,來替換舊的快照 jar 文件。

快照 vs 版本

對於版本,Maven 一旦下載了指定的版本(例如 data-service:1.0),它將不會嘗試從倉庫裏再次下載一個新的 1.0 版本。想要下載新的代碼,數據服務版本須要被升級到 1.1。

對於快照,每次用戶接口團隊構建他們的項目時,Maven 將自動獲取最新的快照(data-service:1.0-SNAPSHOT)。

應用用戶接口 pom.xml

應用用戶接口工程正在使用 1.0 版本的數據服務的快照

<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>app-ui</groupId>   <artifactId>app-ui</artifactId>   <version>1.0</version>   <packaging>jar</packaging>   <name>health</name>   <url>http://maven.apache.org</url>   <properties>      <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>   </properties>   <dependencies>      <dependency>      <groupId>data-service</groupId>          <artifactId>data-service</artifactId>          <version>1.0-SNAPSHOT</version>          <scope>test</scope>      </dependency>   </dependencies> </project>

數據服務 pom.xml

數據服務工程爲每一個微小的變化 release 1.0 快照

<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>data-service</groupId>   <artifactId>data-service</artifactId>   <version>1.0-SNAPSHOT</version>   <packaging>jar</packaging>   <name>health</name>   <url>http://maven.apache.org</url>   <properties>      <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>   </properties>   </project>

雖然,對於快照,Maven 每次自動獲取最新的快照,但你能夠在任何 maven 命令中使用 -U 參數強制 maven 下載最新的快照。

mvn clean package -U

讓咱們打開命令控制檯,進入 C:\ > MVN > app-ui 目錄並執行如下 mvn 命令。

C:\MVN\app-ui>mvn clean package -U

Maven將在下載數據服務的最新快照後,開始構建工程。

[INFO] Scanning for projects... [INFO] ------------------------------------------------------------------- [INFO] Building consumerBanking [INFO]     task-segment: [clean, package] [INFO] ------------------------------------------------------------------- [INFO] Downloading data-service:1.0-SNAPSHOT [INFO] 290K downloaded. [INFO] [clean:clean {execution: default-clean}] [INFO] Deleting directory C:\MVN\app-ui\target [INFO] [resources:resources {execution: default-resources}] [WARNING] Using platform encoding (Cp1252 actually) to copy filtered resources, i.e. build is platform dependent! [INFO] skip non existing resourceDirectory C:\MVN\app-ui\src\main\ resources [INFO] [compiler:compile {execution: default-compile}] [INFO] Compiling 1 source file to C:\MVN\app-ui\target\classes [INFO] [resources:testResources {execution: default-testResources}] [WARNING] Using platform encoding (Cp1252 actually) to copy filtered resources, i.e. build is platform dependent! [INFO] skip non existing resourceDirectory C:\MVN\app-ui\src\test\ resources [INFO] [compiler:testCompile {execution: default-testCompile}] [INFO] Compiling 1 source file to C:\MVN\app-ui\target\test-classes [INFO] [surefire:test {execution: default-test}] [INFO] Surefire report directory: C:\MVN\app-ui\target\ surefire-reports ------------------------------------------------------- T E S T S ------------------------------------------------------- Running com.companyname.bank.AppTest Tests run: 1, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.027 sec  Results :  Tests run: 1, Failures: 0, Errors: 0, Skipped: 0  [INFO] [jar:jar {execution: default-jar}] [INFO] Building jar: C:\MVN\app-ui\target\ app-ui-1.0-SNAPSHOT.jar [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------------ [INFO] Total time: 2 seconds [INFO] Finished at: Tue Jul 10 16:52:18 IST 2012 [INFO] Final Memory: 16M/89M [INFO] ------------------------------------------------------------------------

 

Maven - 構建自動化

構建自動化定義爲一種場景:一旦該工程成功構建完成,其相關的依賴工程即開始構建,目的是爲了保證其依賴項目的穩定。

實例

考慮一個團隊正在開發一個關於總線核心 Api(稱其爲 bus-core-api)的工程,依賴它的工程有 2 個,分別爲網頁 UI(稱其爲 app-web-ui)和應用程序桌面 UI(稱其爲 app-desktop-ui)。

app-web-ui 工程使用 1.0-SNAPSHOT 總線核心 Api 工程,其 POM 文件以下:

<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>app-web-ui</groupId>    <artifactId>app-web-ui</artifactId>    <version>1.0</version>    <packaging>jar</packaging>    <dependencies>       <dependency>       <groupId>bus-core-api</groupId>          <artifactId>bus-core-api</artifactId>          <version>1.0-SNAPSHOT</version>       </dependency>    </dependencies> </project>

app-desktop-ui 工程也正在使用 1.0-SNAPSHOT 總線核心 Api 工程,其 POM 文件以下:

<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>app-desktop-ui</groupId>    <artifactId>app-desktop-ui</artifactId>    <version>1.0</version>    <packaging>jar</packaging>    <dependencies>       <dependency>       <groupId>bus-core-api</groupId>          <artifactId>bus-core-api</artifactId>          <version>1.0-SNAPSHOT</version>       </dependency>    </dependencies> </project>

bus-core-api 工程的 POM 文件以下:

<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>bus-core-api</groupId>    <artifactId>bus-core-api</artifactId>    <version>1.0-SNAPSHOT</version>    <packaging>jar</packaging>    </project>

如今,app-web-ui 和 app-desktop-ui 工程的團隊須要保證當 bus-core-api 工程有變化時他們本身相應的工程能夠隨時被構建。

使用快照能夠保證最新的 bus-core-api 工程能夠被使用,可是爲了達到上述的需求,咱們仍需作一些額外的工做。

咱們有 2 種方式:

  • 在 bus-core-api 的 pom 文件裏添加一個編譯目標來提醒 app-web-ui 工程和 app-desktop-ui 工程啓動建立。
  • 使用一個持續集成(CI)的服務器,好比 Hudson,來實現自動化建立。

使用 Maven

更新 bus-core-api 工程的 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>bus-core-api</groupId>    <artifactId>bus-core-api</artifactId>    <version>1.0-SNAPSHOT</version>    <packaging>jar</packaging>    <build>    <plugins>    <plugin>    <artifactId>maven-invoker-plugin</artifactId>    <version>1.6</version>       <configuration>          <debug>true</debug>          <pomIncludes>             <pomInclude>app-web-ui/pom.xml</pomInclude>             <pomInclude>app-desktop-ui/pom.xml</pomInclude>           </pomIncludes>       </configuration>       <executions>          <execution>             <id>build</id>             <goals>                <goal>run</goal>             </goals>          </execution>       </executions>    </plugin>    </plugins>    <build> </project>

打開命令終端,進入到 C:\ > MVN > bus-core-api 的目錄下,而後執行以下的 mvn 的命令。

C:\MVN\bus-core-api>mvn clean package -U

Maven 將會開始構建 bus-core-api 工程,輸出日誌以下:

[INFO] Scanning for projects... [INFO] ------------------------------------------------------------------ [INFO] Building bus-core-api [INFO]    task-segment: [clean, package] [INFO] ------------------------------------------------------------------ ... [INFO] [jar:jar {execution: default-jar}] [INFO] Building jar: C:\MVN\bus-core-ui\target\ bus-core-ui-1.0-SNAPSHOT.jar [INFO] ------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------

一旦 bus-core-api 構建成功,Maven 將會自動開始構建 app-web-ui 項目, 日誌以下:

[INFO] ------------------------------------------------------------------ [INFO] Building app-web-ui  [INFO]    task-segment: [package] [INFO] ------------------------------------------------------------------ ... [INFO] [jar:jar {execution: default-jar}] [INFO] Building jar: C:\MVN\app-web-ui\target\ app-web-ui-1.0-SNAPSHOT.jar [INFO] ------------------------------------------------------------------ [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------

等到 app-web-ui 建立成功,Maven 接着開始構建 app-desktop-ui 工程,日誌輸出以下:

[INFO] ------------------------------------------------------------------ [INFO] Building app-desktop-ui  [INFO]    task-segment: [package] [INFO] ------------------------------------------------------------------ ... [INFO] [jar:jar {execution: default-jar}] [INFO] Building jar: C:\MVN\app-desktop-ui\target\ app-desktop-ui-1.0-SNAPSHOT.jar [INFO] ------------------------------------------------------------------- [INFO] BUILD SUCCESSFUL [INFO] -------------------------------------------------------------------

使用持續集成服務器(CI)

因爲開發人員不須要每次多一個新的依賴工程時都去更新 bus-core-api 工程的 pom 文件, 所以使用一個持續集成的服務器更加合適,例如,添加一個新的 app-mobile-ui 的工程,它一樣依賴於 bus-core-ui 工程。Hudson 將會藉助 Maven 的依賴管理功能實現工程的自動化建立。

automated build

Hunson 把每次建立工程看作一個工做。一旦工程代碼合入到 svn 或者其餘任何的映射到Hudson上的代碼源管理工具上,Hunson 便開始一次的建立工做,等到該工做完成後,它將會自動建立其餘相關的依賴工做或者依賴工程。

在上面的例子中,當 bus-core-api 的源代碼在 SVN 上有更新時, Hudson 將會啓動建立。當建立完成後,Hudson 開始自動尋找其依賴的工程,而後啓動 app-web-ui 和 app-desktop-ui 工程。

 



 

Maven - 依賴管理

 

Maven 核心特色之一是依賴管理。一旦咱們開始處理多模塊工程(包含數百個子模塊或者子工程)的時候,模塊間的依賴關係就變得很是複雜,管理也變得很困難。針對此種情形,Maven 提供了一種高度控制的方法。

 

傳遞依賴發現

 

這種情形常常可見,當一個庫 A 依賴於其餘庫 B. 另外一工程 C 想要使用庫 A, 那麼該工程一樣也須要使用到庫 B。

 

Maven 能夠避免去搜索全部須要的庫資源的這種需求。經過讀取工程文件(pom.xml)中的依賴項,Maven 能夠找出工程之間的依賴關係。

 

咱們只須要在每一個工程的 pom 文件裏去定義直接的依賴關係。Maven 則會自動的來接管後續的工做。

 

經過傳遞依賴,全部被包含的庫的圖形可能會快速的增加。當重複的庫存在時,可能出現的情形將會持續上升。Maven 提供一些功能來控制可傳遞的依賴的程度。

 

功能
功能描述
依賴調節 決定當多個手動建立的版本同時出現時,哪一個依賴版本將會被使用。 若是兩個依賴版本在依賴樹裏的深度是同樣的時候,第一個被聲明的依賴將會被使用。
依賴管理 直接的指定手動建立的某個版本被使用。例如當一個工程 C 在本身的以來管理模塊包含工程 B,即 B 依賴於 A, 那麼 A 便可指定在 B 被引用時所使用的版本。
依賴範圍 包含在構建過程每一個階段的依賴。
依賴排除 任何可傳遞的依賴均可以經過 "exclusion" 元素被排除在外。舉例說明,A 依賴 B, B 依賴 C,所以 A 能夠標記 C 爲 「被排除的」。
依賴可選 任何可傳遞的依賴能夠被標記爲可選的,經過使用 "optional" 元素。例如:A 依賴 B, B 依賴 C。所以,B 能夠標記 C 爲可選的, 這樣 A 就能夠再也不使用 C。

 

依賴範圍

 

傳遞依賴發現能夠經過使用以下的依賴範圍來獲得限制:

 

範圍
描述
編譯階段 該範圍代表相關依賴是隻在工程的類路徑下有效。默認取值。
供應階段 該範圍代表相關依賴是由運行時的 JDK 或者 網絡服務器提供的。
運行階段 該範圍代表相關依賴在編譯階段不是必須的,可是在執行階段是必須的。
測試階段 該範圍代表相關依賴只在測試編譯階段和執行階段。
系統階段 該範圍代表你須要提供一個系統路徑。
導入階段 該範圍只在依賴是一個 pom 裏定義的依賴時使用。同時,當前工程的POM 文件的部分定義的依賴關係能夠取代某特定的 POM。

 

依賴管理

 

一般狀況下,在一個共通的工程下,有一系列的工程。在這種狀況下,咱們能夠建立一個公共依賴的 pom 文件,該 pom 包含全部的公共的依賴關係,咱們稱其爲其餘子工程 pom 的 pom 父。 接下來的一個例子能夠幫助你更好的理解這個概念。

 

dependency graph

 

下面是上述依賴圖表的細節:

 

  • App-UI-WAR 依賴於 App-Core-lib 和 App-Data-lib.
  • Root 是 App-Core-lib 和 App-Data-lib 的父類。
  • Root 在其依賴模塊裏定義了 Lib1,lib2, Lib3 3個依賴關係。

 

App-UI-WAR 的 POM 文件以下:

 

<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.companyname.groupname</groupId>       <artifactId>App-UI-WAR</artifactId>       <version>1.0</version>       <packaging>war</packaging>       <dependencies>          <dependency>             <groupId>com.companyname.groupname</groupId>             <artifactId>App-Core-lib</artifactId>             <version>1.0</version>          </dependency>       </dependencies>         <dependencies>          <dependency>             <groupId>com.companyname.groupname</groupId>             <artifactId>App-Data-lib</artifactId>             <version>1.0</version>          </dependency>       </dependencies>   </project>

 

App-Core-lib 的 POM 文件以下:

 

<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">       <parent>          <artifactId>Root</artifactId>          <groupId>com.companyname.groupname</groupId>          <version>1.0</version>       </parent>       <modelVersion>4.0.0</modelVersion>       <groupId>com.companyname.groupname</groupId>       <artifactId>App-Core-lib</artifactId>       <version>1.0</version>        <packaging>jar</packaging> </project>

 

App-Data-lib 的 POM 文件以下:

 

<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">       <parent>          <artifactId>Root</artifactId>          <groupId>com.companyname.groupname</groupId>          <version>1.0</version>       </parent>       <modelVersion>4.0.0</modelVersion>       <groupId>com.companyname.groupname</groupId>       <artifactId>App-Data-lib</artifactId>       <version>1.0</version>          <packaging>jar</packaging> </project>

 

Root 的 POM 文件以下:

 

<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.companyname.groupname</groupId>       <artifactId>Root</artifactId>       <version>1.0</version>       <packaging>pom</packaging>       <dependencies>          <dependency>             <groupId>com.companyname.groupname1</groupId>             <artifactId>Lib1</artifactId>             <version>1.0</version>          </dependency>       </dependencies>         <dependencies>          <dependency>             <groupId>com.companyname.groupname2</groupId>             <artifactId>Lib2</artifactId>             <version>2.1</version>          </dependency>       </dependencies>         <dependencies>          <dependency>             <groupId>com.companyname.groupname3</groupId>             <artifactId>Lib3</artifactId>             <version>1.1</version>          </dependency>       </dependencies>   </project>

 

如今,當咱們構建 App-UI-WAR 工程時, Maven 將會經過遍歷依賴圖找到全部的依賴關係,而且構建該應用程序。

 

經過上面的例子,咱們能夠學習到如下關鍵概念:

 

  • 公共的依賴可使用 pom 父的概念被統一放在一塊兒。App-Data-lib 和 App-Core-lib 工程的依賴在Root 工程裏列舉了出來(參考 Root的包類型,它是一個 POM).
  • 沒有必要在 App-UI-W 裏聲明 Lib1, lib2, Lib3 是它的依賴。 Maven 經過使用可傳遞的依賴機制來實現該細節。


 

Maven - 自動化部署

 

通常狀況下,在一個工程開發進程裏,一次部署的過程包含需以下步驟:

 

  • 合入每一個子工程下的代碼到 SVN 或者源代碼庫,並標記它。
  • 從 SVN 下載完整的源代碼。
  • 構建應用程序。
  • 保存構建結果爲 WAR 或者 EAR 類型文件並存放到一個共同的指定的網絡位置上。
  • 從網絡上得到該文件而且部署該文件到產品線上。
  • 更新文檔日期和應用程序的版本號。

 

問題陳述

 

一般,將會有不少不一樣的人蔘與到上述部署過程當中。一個團隊能夠負責代碼的合入工做,另一個能夠負責構建,以此類推。上述的任何一個步驟均可能由於人爲的緣由沒有被執行。例如,較舊的版本沒有在網絡機器上更新,負責部署的團隊再一次部署了舊的版本。

 

解決方案

 

經過結合以下的方案來實現自動化部署:

 

  • Maven 構建和發佈項目,
  • SubVersion, 源代碼庫用以管理源代碼,
  • 遠程倉庫管理工具 (Jfrog/Nexus) 用以管理工程的二進制文件。

 

更新工程的 POM.xml

 

咱們將會使用 Maven 發佈的插件來建立一個自動化發佈過程:

 

例如: bus-core-api 工程的 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>bus-core-api</groupId>    <artifactId>bus-core-api</artifactId>    <version>1.0-SNAPSHOT</version>    <packaging>jar</packaging>     <scm>       <url>http://www.svn.com</url>       <connection>scm:svn:http://localhost:8080/svn/jrepo/trunk/       Framework</connection>       <developerConnection>scm:svn:${username}/${password}@localhost:8080:       common_core_api:1101:code</developerConnection>    </scm>    <distributionManagement>       <repository>          <id>Core-API-Java-Release</id>          <name>Release repository</name>          <url>http://localhost:8081/nexus/content/repositories/          Core-Api-Release</url>       </repository>    </distributionManagement>    <build>       <plugins>          <plugin>             <groupId>org.apache.maven.plugins</groupId>             <artifactId>maven-release-plugin</artifactId>             <version>2.0-beta-9</version>             <configuration>                <useReleaseProfile>false</useReleaseProfile>                <goals>deploy</goals>                <scmCommentPrefix>[bus-core-api-release-checkin]-<                /scmCommentPrefix>             </configuration>          </plugin>       </plugins>    </build> </project>

 

在 pom.xml 裏,咱們經常會使用到的重要元素以下表:

 

元素
描述
SCM 配置 SVN 的路徑,Maven 將從該路徑下將代碼取下來。
倉庫 成功構建出來的 WAR/EAR/JAR 或者其餘的構建結果存放的路徑。
插件 maven-release-plugin 用以自動化部署的過程。

 

Maven Release 插件

 

Maven 經過 maven-release-plugin 來執行以下頗有用的任務:

 

mvn release:clean

 

清理工做空間,保證最新的發佈進程成功進行。

 

mvn release:rollback

 

回滾修改的工做空間代碼和配置保證發佈過程成功進行。

 

mvn release:prepare

 

執行以下屢次操做:

 

  • 檢查本地是否存在還未提交的修改
  • 確保沒有快照的依賴
  • 改變應用程序的版本信息用以發佈
  • 更新 POM 文件到 SVN
  • 運行測試用例
  • 提交修改後的 POM 文件
  • 爲代碼在 SVN 上作標記
  • 增長版本號和附加快照以備未來發布
  • 提交修改後的 POM 文件到 SVN.

 

mvn release:perform

 

將代碼切換到以前作標記的地方,運行 Maven 部署目標來部署 WAR 文件或者構建相應的結構到倉庫裏。

 

打開命令終端,進入到 C:\ > MVN >bus-core-api 目錄下,而後執行以下的 mvn 命令。

 

C:\MVN\bus-core-api>mvn release:prepare

 

Maven 開始構建整個工程。一旦構建成功便可運行以下 mvn 命令。

 

C:\MVN\bus-core-api>mvn release:perform

 

一旦構建成功,你能夠驗證在你倉庫下上傳的 JAR 文件是否生效。

 

Maven - Web 應用

本教程將指導你如何使用 Maven 版本控制系統來管理一個基於 Web 的工程。在此,你將學習到如何建立/構建/部署以及運行 Web 應用程序:

建立 Web 應用

創建一個簡單的 Java web 應用,咱們可使用 maven-archetype-webapp 插件。首先咱們打開命令控制檯,進入 C:\MVN 目錄而且執行如下的 mvn 命令。

C:\MVN>mvn archetype:generate  -DgroupId=com.companyname.automobile  -DartifactId=trucks -DarchetypeArtifactId=maven-archetype-webapp  -DinteractiveMode=false

Maven 將開始處理而且將建立完整的基於 Web 的 java 應用工程結構。

[INFO] Scanning for projects... [INFO] Searching repository for plugin with prefix: 'archetype'. [INFO] ------------------------------------------------------------------- [INFO] Building Maven Default Project [INFO]    task-segment: [archetype:generate] (aggregator-style) [INFO] ------------------------------------------------------------------- [INFO] Preparing archetype:generate [INFO] No goals needed for project - skipping [INFO] [archetype:generate {execution: default-cli}] [INFO] Generating project in Batch mode [INFO] -------------------------------------------------------------------- [INFO] Using following parameters for creating project  from Old (1.x) Archetype: maven-archetype-webapp:1.0 [INFO] -------------------------------------------------------------------- [INFO] Parameter: groupId, Value: com.companyname.automobile [INFO] Parameter: packageName, Value: com.companyname.automobile [INFO] Parameter: package, Value: com.companyname.automobile [INFO] Parameter: artifactId, Value: trucks [INFO] Parameter: basedir, Value: C:\MVN [INFO] Parameter: version, Value: 1.0-SNAPSHOT [INFO] project created from Old (1.x) Archetype in dir: C:\MVN\trucks [INFO] ------------------------------------------------------------------- [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------- [INFO] Total time: 16 seconds [INFO] Finished at: Tue Jul 17 11:00:00 IST 2012 [INFO] Final Memory: 20M/89M [INFO] -------------------------------------------------------------------

如今進入 C:/MVN 目錄,你將看到一個名爲 trucks(由 artifactld 指定)的 java 應用工程。

Java web application project structure

Maven 使用一個標準的目錄架構,如上示例,咱們能夠理解如下的關鍵概念:

文件夾結構
描述
trucks 包含 src 文件夾和 pom.xml
src/main/webapp 包含 index.jsp 和 WEB-INF 文件夾.
src/main/webapp/WEB-INF 包含 web.xml
src/main/resources 包含 images / properties 文件。

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/maven-v4_0_0.xsd">    <modelVersion>4.0.0</modelVersion>    <groupId>com.companyname.automobile</groupId>    <artifactId>trucks</artifactId>    <packaging>war</packaging>    <version>1.0-SNAPSHOT</version>    <name>trucks Maven Webapp</name>    <url>http://maven.apache.org</url>    <dependencies>       <dependency>          <groupId>junit</groupId>          <artifactId>junit</artifactId>          <version>3.8.1</version>          <scope>test</scope>       </dependency>    </dependencies>    <build>       <finalName>trucks</finalName>    </build> </project>

若是仔細觀察,Maven 還建立了一個示例 JSP 的源文件。

打開 C:\ > MVN > trucks > src > main > webapp > 文件夾, 你將看到 index.jsp.

<html>    <body>       <h2>Hello World!</h2>    </body> </html>

Build Web Application

打開終端,進入 C:\MVN\trucks 目錄,而後執行以下 mvn 命令.

C:\MVN\trucks>mvn clean package

Maven 將會開始構建此工程,日誌輸出以下:

[INFO] Scanning for projects... [INFO] ------------------------------------------------------------------- [INFO] Building trucks Maven Webapp [INFO]    task-segment: [clean, package] [INFO] ------------------------------------------------------------------- [INFO] [clean:clean {execution: default-clean}] [INFO] [resources:resources {execution: default-resources}] [WARNING] Using platform encoding (Cp1252 actually) to  copy filtered resources,i.e. build is platform dependent! [INFO] Copying 0 resource [INFO] [compiler:compile {execution: default-compile}] [INFO] No sources to compile [INFO] [resources:testResources {execution: default-testResources}] [WARNING] Using platform encoding (Cp1252 actually) to  copy filtered resources,i.e. build is platform dependent! [INFO] skip non existing resourceDirectory  C:\MVN\trucks\src\test\resources [INFO] [compiler:testCompile {execution: default-testCompile}] [INFO] No sources to compile [INFO] [surefire:test {execution: default-test}] [INFO] No tests to run. [INFO] [war:war {execution: default-war}] [INFO] Packaging webapp [INFO] Assembling webapp[trucks] in [C:\MVN\trucks\target\trucks] [INFO] Processing war project [INFO] Copying webapp resources[C:\MVN\trucks\src\main\webapp] [INFO] Webapp assembled in[77 msecs] [INFO] Building war: C:\MVN\trucks\target\trucks.war [INFO] ------------------------------------------------------------------- [INFO] BUILD SUCCESSFUL [INFO] ------------------------------------------------------------------- [INFO] Total time: 3 seconds [INFO] Finished at: Tue Jul 17 11:22:45 IST 2012 [INFO] Final Memory: 11M/85M [INFO] -------------------------------------------------------------------

部署 Web 應用

如今拷貝在 C:\ > MVN > trucks > target > 文件夾下的 trucks.war 到你的 web 服務器的 webapp 目錄下,而且重啓 web 服務。

測試 Web 應用

使用 URL: http://\<server-name>:\<port-number>/trucks/index.jsp 來運行你的 Web 應用。

驗證輸出結果:

web page

相關文章
相關標籤/搜索