Maven指南(二)POM文件说明 及依赖管理

POM
  pom是Maven工作的基本单元,每个项目只会有一个pom.xml文件,其中包含项目对象、构建流程和其它配置信息。当构建项目时,Maven通过读取pom.xml获取配置信息然后执行相应的有序操作。

超级POM
  Maven自带了一个Super POM,也是Maven的默认POM。除非明确设置,否则所有POM都会扩展Super POM,这意味着在Super POM中的配置信息将由所有子项目继承。Super Pom文件通常位于 maven安装目录\lib\maven-model-builder-3.5.2.jar\org\apache\maven\model\pom-4.0.0.xml,其中声明了Maven的远程仓库地址https://repo.maven.apache.org/maven2/ 、项目默认构建路径等信息。
注:在没有指定仓库位置的情况下,将继承Super POM中的存储库配置http://repo.maven.apache.org/maven2。但如果公司搭建了内部存储仓库(也称私服),就可以通过配置指定从私服上下载依赖,私服在这里起到一个代理的作用。
下面是摘取自pom-4.0.0.xml的相关配置


  4.0.0
  
  
    
      central
      Central Repository
      https://repo.maven.apache.org/maven2
      
      default
      
      
        false
      
    
  
 
  
  
    
      central
      Central Repository
      https://repo.maven.apache.org/maven2    
      default
      
        false
      
      
      
        never
      
    
  
  
  
    ${project.basedir}/target
    ${project.build.directory}/classes
    ${project.artifactId}-${project.version}
    ${project.build.directory}/test-classes
    ${project.basedir}/src/main/java
    ${project.basedir}/src/main/scripts
    ${project.basedir}/src/test/java
    
      
        ${project.basedir}/src/main/resources
      
    
    
      
        ${project.basedir}/src/test/resources
      
    
    
  
   

 最小POM
  一个最小的pom文件至少需要配置modelVersion、groupId(组ID)、artifactId(项目ID)、version四个标识,其中后三者的组合代表了(在Maven中)项目的唯一坐标。其中groupId定义项目所属组织,artifactId定义当前项目在组中的唯一ID。
  以常见的spring为例,它们的groupId相同,但artifactId不一样。


	org.springframework.boot
	spring-boot-starter



	 org.springframework.boot 
	 spring-boot-devtools 
	true

  同样的,如果你公司有一个项目a,它由很多组件构件,有核心组件b,公共组件c等,那么它们的groupId就都可以定义成com.youcompany.a,然后artifactId就可以core、comment等等。 
Maven指南(二)POM文件说明 及依赖管理_第1张图片  

POM继承
   
maven支持pom之间继承,通常由父pom.xml进行公共配置,子pom中配置项目独需信息即可,父pom的打包方式必须为pom。实际开发中,有时会对项目按层结构或按模块进行拆分,拆分成多个子项目,这种情况下,子项目一般都有相同的groupid和vesion,并且会有一些公共的依赖,这种情况下父pom的存在就很有必要。

POM聚合
 当需要一次性打包多个项目(模块)时,而不是一个一个执行mvn命令,可以用聚合的方式,聚合POM的打包方式也必须是pom。为了方便构建,通常聚合模块作为项目的顶层项目,而其它子项目作为聚合目录下的子目录存在,这点会在POM聚合与继承的进行说明。

POM聚合与继承
  通常同时构建的多个项目(模块)间是存在继承关系的,这种情况下就可以结合使用POM聚合与继承,也就是一个pom即是父pom同时也是一个聚合POM。这里简述一个实际案例,原有项目emptablerate按公司规范需要按层+模块拆分成多个项目,拆分后如下(创建流程:先创建一个父项目,在其pom中包含其它子项目),默认情况下子项目会作为聚合项目的子目录存在。
     构建时,直接在父项目上执行mvn命令即会一次性对所有模块进行构建。
Maven指南(二)POM文件说明 及依赖管理_第2张图片Maven指南(二)POM文件说明 及依赖管理_第3张图片

...
	
		0.0.1-SNAPSHOT
	
	
	4.0.0
	cn.cloudwalk.emptyseatrate
	cloudwalk-emptyseatrate-parent
	0.0.1-SNAPSHOT
	pom

	
		org.springframework.boot
		spring-boot-starter-parent
		2.1.4.RELEASE
		 
	

    
	
		cloudwalk-emptyseatrate-web
		cloudwalk-emptyseatrate-service
		cloudwalk-emptyseatrate-interface
		cloudwalk-emptyseatrate-data
		cloudwalk-emptyseatrate-common
	
	
	
	
		
		
			org.apache.commons
			commons-lang3
		
		
			commons-collections
			commons-collections
			3.2.2	
		
....

依赖管理
   
   依赖管理是Maven的核心功能之一,它提供了dependency:analyze(依赖分析插件)以分析和管理依赖关系。
  依赖传递:由于每个项目都有pom.xml文件,所以Maven可以通过依赖传递来发现所有依赖。
       依赖冲突:当有循环依赖时Maven会通过依赖级别数量进行限制;当有重复依赖时,Maven取依赖关系树中的深度最浅的那个依赖库,如果深度一样则取第一个声明的依赖库。如果依赖的库版本不一样,此时可手动进行依赖关系管理,强制指定使用的版本,或者直接包含某依赖项。  
  依赖范围Scope(想要理解依赖范围,建议先了解Maven构建的生命周期):主要有6种

  • compile:默认的scope,代表在应用编译、测试、运行其间都将该jar(pom最终也是jar)加入到classpath中。
  • provide:代表在应用编译、测试期间需要依赖该项,但实际运行时由运行环境提供,如servlet-api.jar,运行时由Tomcat容器提供,不需要打包。当某个依赖由运行环境提供了时可用该配置。
  • runtime:表示在测试、运行时依赖该项,但编译期间不需要。如JDBC驱动的实现jar在编译期间不需要。
  • test:只有在测试代码的编译和运行阶段需要依赖它。如jutil.jar
  • system:与provide一样,但它是用来指定外部依赖项,而不是本地仓库中的依赖项, 所以它需要通过systemPath来指定依赖项路径。
  • import

  依赖传递时依赖范围确定:下面是Maven官网上关于依赖传递时依赖范围的说明,假设A对B依赖范围为compile,B对C依赖范围为provided,则说明A运行时不需要C(A的编译和测试只需要B的参与就行),但C应该由容器提供,所以在A的环境中C应该已经存在,这种情况下A和C才是无依赖的情况,否则运行时将报出异常。关于这块建议参考:https://seanzhou.iteye.com/blog/1688740

第1列表示A对B的依赖范围
第1行表示B对C的依赖范围
交叉格表示A对C的依赖范围,-表示无依赖关系
compile provided runtime test
compile compile(*) - runtime -
provided provided - provided -
runtime runtime - runtime -
test test - test -


       依赖排除...,依赖排除可以手动控制依赖关系,包括排除、指定、替换依赖等。

  可选依赖:true,可选依赖项不会被传递。通常不建议使用它,使用可选依赖的场景是某一个项目实现了多个特性,如支持多种数据库,包括Mysql、Oracle驱动包等,但最终使用的时候只会是其中一个,这种情况下可以用option,但更好的做法是针对不同数据库提供不同的jar包。

你可能感兴趣的:(Maven指南(二)POM文件说明 及依赖管理)