Maven知識點梳理(持續更新)

Maven一個項目的構建和管理工具

相關配置

項目級:定義在項目的POM文件pom.xml中
用戶級:%USER_HOME%/.m2/settings.xml
全局:%M2_HOME%/conf/settings.xml
父POM:%M2_HOME%/lib/maven-model-builder-3.6.2.jar中的pom文件(這個文件一般不會改動)
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>
  <!--父工程的相關配置 -->
  <parent>
    <groupId>com.xxx</groupId>
    <artifactId>pdemo</artifactId>
    <version>0.0.1-SNAPSHOT</version>
  </parent>
  <!--文檔名 -->
  <artifactId>demo</artifactId>
  <!--包類型 -->
  <packaging>war</packaging>
  <!--依賴 -->
   <dependencies>
	<dependency>
		<groupId>org.springframework.security</groupId>
		<artifactId>spring-security-config</artifactId>		
	</dependency>
  </dependencies>
  <!--工程的構建過程 -->
  <build>
  	 <!--maven插件 -->
	 <plugins>
		<plugin>
			<groupId>org.apache.tomcat.maven</groupId>
			<artifactId>tomcat7-maven-plugin</artifactId>
			<configuration>
				<path>/</path>
				<port>9002</port>
			</configuration>
		</plugin>
	 </plugins>
  </build>
</project>

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>/path/to/local/repo</localRepository>
    <!-- Maven是否需要和用戶交互以獲得輸入 -->	
    <interactiveMode>true</interactiveMode>
    <!-- 是否啓動離線模式 -->	
    <offline>false</offline>
    <!-- 插件的組織ID,使用插件時在這個list裏面搜索,比如什麼都不配,有默認的org.apache.maven.plugins -->
    <pluginGroups>com.your.plugins</pluginGroups>
    <!-- 代理,就是代理自己去訪問遠程服務器,遠程倉庫 -->	
    <proxies>
	    <proxy>
	      <id>optional</id>
	      <active>true</active>
	      <protocol>http</protocol>
	      <username>proxyuser</username>
	      <password>proxypass</password>
	      <host>proxy.host.net</host>
	      <port>80</port>
	      <nonProxyHosts>local.net|some.host.com</nonProxyHosts>
	   </proxy>
   </proxies>
   <!-- 服務器授權信息 -->	
   <servers>
   	  <server>
	     <id>nexus-releases</id>
	     <privateKey>/path/to/private/key</privateKey>
	     <passphrase>optional; leave empty if not used.</passphrase>
	  </server>
   </servers>
   <!-- 鏡像,即對repository重定向 -->	
   <mirrors>
      <mirror>
	 	  <id>mirrorId</id>
		  <!-- 鏡像對應的遠程倉庫,需和倉庫的ID匹配,使用逗號分隔多個遠程倉庫 -->	
		  <mirrorOf>repositoryId</mirrorOf>
		  <name>Human Readable Name for this Mirror.</name>
		  <url>http://my.repository.com/repo/path</url>
	  </mirror>
   </mirrors>
    <!-- 分發管理 。比如我需要把開發的工程打包到遠程倉庫裏做管理-->
   <distributionManagement>    
    <repository>    
      <id>nexus-releases</id>    
      <name>Nexus Release Repository</name>    
      <url>http://127.0.0.1:8080/nexus/content/repositories/releases/</url>    
    </repository>    
    <snapshotRepository>    
      <id>nexus-snapshots</id>    
      <name>Nexus Snapshot Repository</name>    
      <url>http://127.0.0.1:8080/nexus/content/repositories/snapshots/</url>    
    </snapshotRepository>    
  </distributionManagement>
   <!-- 配置信息 -->
   <profiles>
      <profile>
	      <id>jdk-1.4</id>
	      <activation>
	        <jdk>1.4</jdk>
	      </activation>
	      <!-- 遠程倉庫列表 -->	
	      <repositories>
	        <repository>
	          <id>jdk14</id>
	          <name>Repository for JDK 1.4 builds</name>
	          <url>http://www.myhost.com/maven/jdk14</url>
	          <layout>default</layout>
	        </repository>
	      </repositories>
   	  </profile>
   </profiles>
</settings>

理解repository,mirror,server

  • repository
    存放各種jar包和maven插件。當向倉庫請求插件或依賴的時候,會先檢查local repository,如果local repository有則直接返回,否則會向remote repository請求,並緩存到local repository

  • mirror
    把請求裏的remote repository地址,重定向到mirror裏配置的地址。
    比如有A,B兩個repository都可以找到對應資源,A爲公服,B是私服。我把A作爲repository,B作爲mirror,實際訪問的時候會到B,這樣提升了下載速度。並且如果環境變化,我也可以很靈活的在repository或mirror中做切換

  • server
    訪問有的repository或mirror的服務器需配置一些授權信息

profile

理解profile
  • 可以解決項目在不同環境下,用不同的配置信息做構建,或者在不同環境採用不同的構建方式來構建
  • profile在settings.xml,pom.xml裏都可以做配置,如果settings.xml有profile,pom.xml裏沒有,則所有項目都會使用settings.xml裏的profile,如果pom.xml裏有,項目就會使用自己的profile。
配置profile
  • 不同環境,使用不同的配置文件構建項目
    定義profile的相關參數:

    <profiles>
        <profile>
            <!-- 本地開發環境 -->
          	<打包的時候根據該id指定:mvn package -P dev>
            <id>dev</id>
            <properties>
            	<!-- 對應了src/main/resources/dev -->
                <profiles.active>dev</profiles.active>
            </properties>
            <activation>
            	<!-- 默認激活 -->
                <activeByDefault>true</activeByDefault>
            </activation>
        </profile>
        <profile>
            <!-- 測試環境 -->
            <id>test</id>
            <properties>
            	<!-- 對應了src/main/resources/test-->
                <profiles.active>test</profiles.active>
            </properties>
        </profile>
    </profiles>
    

    根據上述參數配置資源的構建過程:

    <build>
        <resources>
            <resource>
                <directory>src/main/resources</directory>
                <excludes>
                    <exclude>test/*</exclude>
                    <exclude>pro/*</exclude>
                    <exclude>dev/*</exclude>
                </excludes>
            </resource>
            <resource>
                <directory>src/main/resources/${profiles.active}</directory>
            </resource>
        </resources>
    </build>
    
  • 同一配置文件,通過替換佔位符,被賦予不同的值
    定義profile的相關參數:

    <profiles>
    	<profile>
    	   <id>dev</id>
    	   <properties>
    		   <db.url>localhost</database.host>
    	   </properties>
    	</profile>
    	<profile>
    		<id>test</id>
    		<properties>
    			<db.url>192.168.142.154</database.host>
    		</properties>
    	</profile>
    <profiles>
    

    構建資源的配置:

    <build>
      <resources>
        <resource>
          <directory>src/main/resources</directory>
    	  <!-- 開啓替換佔位符 -->
          <filtering>true</filtering>
        </resource>
      </resources>
    </build>
    

    配置文件:
    src/main/resources/db.properties

    database.pool.url=${db.url}
    
  • 不同環境,用不同的構建方式做構建
    只需要把build的相關內容寫到profile裏面即可

Maven項目主要構建過程(build)

  1. clean(清除)
  2. default-validate(缺省驗證)
  3. initialize(初始化)
  4. generate-sources, process-sources, generate-resources, process-resources(加載運行資源)
  5. compile(編譯)
  6. test(執行測試用例)
  7. package(打包)
  8. verify(驗證)
  9. install(安裝)
  10. deploy(部署)

常用指令

  • mvn clean
    清除歷史打的包(即刪除target文件夾,不影響本地的maven庫)

  • mvn compile
    項目編譯(就是生成class文件)

  • mvn package
    項目編譯打包

  • mvn xxx -Dmaven.skip.test=true
    跳過測試,對測試用例不編譯也不執行

  • mvn xxx -DskipTests
    跳過測試,對測試用例不執行但會編譯

  • mvn install
    項目編譯打包並安裝到本地maven庫(解決項目間的依賴問題)

  • mvn install:install-file -DgroupId=org.freemarker -DartifactId=freemarker -Dversion=2.3.23 -Dpackaging=jar -Dfile=J:\freemarker-2.3.23.jar
    手動加入文檔到maven庫裏(解決引入在中央倉庫裏沒有的jar包問題)

  • mvn clean install -e -U :-e詳細異常,-U強制更新

  • mvn clean package -Ptest :按profile爲test的配置打包

Maven的打包規則

jar

  • 默認規則
    在這裏插入圖片描述
    項目路徑下的target目錄爲maven的項目構建目錄
    src/main/java 裏面的*.java文件會被編譯,並將生成的*.class放到target/classes目錄下
    src/main/java 裏面的其他文件,不會做任何操作
    src/main/resources裏面的文件,會被直接拷貝到target/classes目錄下
    src/test/java 裏面的*.java文件會被編譯,並將生成的*.class放到target/test-classes目錄下
    src/test/java 裏面的其他文件,不會做任何操作
    src/test/resources裏面的文件,會被直接拷貝到target/test-classes目錄下
    target/classes目錄下的文件會被最終打到jar包裏

  • 通過Maven插件,自定義打包規則

war

  • 默認規則
    在這裏插入圖片描述
    項目路徑下的target目錄爲maven的項目構建目錄
    src/main/java的處理規則同jar包
    src/main/resources的處理規則同jar包
    src/test/java的處理規則同jar包
    src/test/resources的處理規則同jar包
    webapp裏面的的文件,會被直接拷貝到與最終打出的war包同名的一個文件夾下
    target/classes目錄下的文件會被直接拷貝到與最終打出的war包同名的一個文件夾下的WEB-INF/classes目錄下
    項目的相關依賴會被拷貝到與最終打出的war包同名的一個文件夾下的WEB-INF/lib目錄下
    與最終打出的war包同名的文件夾下的文件會被打包成war包
  • 通過Maven插件,自定義打包規則

使用maven插件

Maven生命週期的階段(phase)默認綁定的插件目標

在這裏插入圖片描述
在這裏插入圖片描述
在這裏插入圖片描述冒號後面即是綁定的插件目標,冒號前面是插件的前綴(prefix)
關於插件的前綴(prefix),比如我們平常寫的:

<!-- maven-${prefix}-plugin-->
<artifactId>maven-compiler-plugin</artifactId>
<!-- ${prefix}-maven-plugin-->
<artifactId>tomcat7-maven-plugin</artifactId>

關於插件目標(goal):爲了能夠複用代碼,它往往能夠完成多個任務, 這些功能聚集在一個插件裏,每個功能就是一個目標。

配置插件所綁定的生命週期(Maven默認綁定的插件不需要配置)

<plugin>
	<groupId>org.apache.maven.plugins</groupId>
	<artifactId>maven-dependency-plugin</artifactId>
   	<executions>
       	<execution>
       	   <!--id:就是個唯一標識,隨便寫-->
           <id>copy</id>
           <!--phase:即綁定的生命週期-->
           <phase>install</phase>
           <goals>
           	   <!--goal:即執行的插件目標-->
               <goal>copy-dependencies</goal>
           </goals>
           <configuration>
               <outputDirectory>${project.build.directory}/lib</outputDirectory>
           </configuration>
       	</execution>
     </executions>
</plugin>

常用插件

  • tomcat7-maven-plugin:Maven內置的tomcat

  • maven-compiler-plugin:Maven編譯時用的插件

  • maven-resources-plugin:Maven處理項目資源文件並拷貝到輸出(構建)目錄的插件

  • maven-dependency-plugin:Maven的依賴插件,負責將maven的相關依賴輸出到指定目錄

  • maven-jar-plugin:Maven用來打jar包的插件。可指明jar包生成位置,jar的入口類

  • maven-assembly-plugin:與maven-jar-plugin類似

  • maven-shade-plugin:Maven用來打jar的插件。可做更多詳細的配置,比如:將部分jar包添加或排除,將jar包內部資源添加或排除,將依賴的類重命名並打包進來,修改包的後綴名:

  • maven-war-plugin:Maven用來打war的插件。可以配置具體哪些資源被打到什麼位置等

  • maven-source-plugin:把源碼也打到包裏

插件使用綜合實例

  • 使用Maven內置的tomcat啓動服務
    相關指令: tomcat7:run ,tomcat7:exec-war , tomcat7:exec-war-only

    <plugin>
    		<groupId>org.apache.tomcat.maven</groupId>
    		<artifactId>tomcat7-maven-plugin</artifactId>
    		<version>2.2</version>
    		<configuration>
    			<!-- 指定端口 -->
    			<port>9090</port>
    			<!-- 請求路徑 -->
    			<path>/</path>
    		</configuration>
    </plugin>
    
  • 指定編譯的JDK版本和編碼格式

    <plugin>
    		<groupId>org.apache.maven.plugins</groupId>
    		<artifactId>maven-compiler-plugin</artifactId>
    		<version>3.2</version>
    		<configuration>
    			<source>1.8</source>
    			<target>1.8</target>
    			<encoding>UTF-8</encoding>
    		</configuration>
    </plugin>
    
  • 以com.alibaba.dubbo.container.Main作爲啓動類打jar包

    <plugin>
    	<groupId>org.apache.maven.plugins</groupId>
    	<artifactId>maven-jar-plugin</artifactId>
    	<configuration>
    		<classesDirectory>target/classes/</classesDirectory>
    		<archive>
    			<manifest>
    				<mainClass>com.alibaba.dubbo.container.Main</mainClass>
    				<useUniqueVersions>false</useUniqueVersions>
    				<addClasspath>true</addClasspath>
    				<classpathPrefix>lib/</classpathPrefix>
    			</manifest>
    			<manifestEntries>
    				<Class-Path>.</Class-Path>
    			</manifestEntries>
    		</archive>
    	</configuration>
    </plugin>
    
  • 打jar包時,把依賴拷貝到構建目錄下

    <plugin>
    	 <groupId>org.apache.maven.plugins</groupId>
    	 <artifactId>maven-dependency-plugin</artifactId>
      	 <executions>
    	     <execution>
    	         <id>copy</id>
    	         <phase>install</phase>
    	         <goals>
    	             <goal>copy-dependencies</goal>
    	         </goals>
    	         <configuration>
    	             <outputDirectory>${project.build.directory}/lib</outputDirectory>
    	         </configuration>
    	     </execution>
      	 </executions>
    </plugin>
    

報錯

  • 項目啓動報錯
    Invalid byte 3 of 3-byte UTF-8 sequence
    在這裏插入圖片描述
    解決:
    maven-resources-plugin不指定的話,maven默認使用平臺的編碼格式
    <plugin>  
          <groupId>org.apache.maven.plugins</groupId>  
          <artifactId>maven-resources-plugin</artifactId>  
          <configuration>  
              <encoding>UTF-8</encoding>  
          </configuration>  
    </plugin>
    
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章