Maven笔记

原文:https://www.yuque.com/uy2gee/yfyp6h/maven

Maven配置

Maven配置生效原则

默认情况:配置生效(从前往后进行覆盖,不同配置合并)

  • ~/.m2文件下 settings.xml
  • 本机安装的apache maven文件下conf/settings.xml
  • 项目中pom.xml

其本质:~/.m2/settings.xml是约定,在IDEA中maven默认指定了这个文件路径,使用时会遵循上述的默认情况,如果我们在IDEA中指定了maven的settings.xml的路径,那么~/.m2/settings.xml就不会生效

Pom中的profile机制

profile 里所配置的东西,在正常情况下是不会生效的,想要生效要指定激活他才行。

配置

<profiles>
  <profile>
    <id>dev</id>
    <properties>
      <!--环境-->
      <spring.profiles.active>dev</spring.profiles.active>
    </properties>
    <activation>
      <!--默认是否开启-->
      <activeByDefault>true</activeByDefault>
    </activation>
  </profile>
</profiles>

生效方式

-P参数指定 : mvn install -Pdev

默认启动参数总开启:activeByDefault

IDEA开发工具中勾选:

Maven的依赖机制

坐标机制

groupId + artifactId + version + packaging + classifier,五个维度的坐标,唯一定位一个依赖包

任何一个项目,都是用这五个维度唯一定位一个发布包

实际上后面两个维度较为少用,99%的场景下,唯一定位一个依赖的就是三个维度,groupId + artifactId + version

groupId:组织ID

artifactId:项目模块ID

version

版本号

SNAPSHOT:SNAPSHOT后缀的版本是非稳定版本,每次打包的时候都会重新去仓库拉取,deploy可以一直覆盖,其余版本号都是release版本,deploy后不能覆盖,只能在私服操作删除后再次进行提交。

packaging

目前支持以下三种配置:

<packaging>pom</packaging>
<packaging>jar</packaging>
<packaging>war</packaging>

引用的时候使用的时<type>标签

classifier

<dependency>
  <groupId>org.hibernate</groupId>
  <artifactId>hibernate-hikaricp</artifactId>
  <version>1.0.0</version>
  <type>jar</type>
  <classifier>jdk8</classifier>
</dependency>

查找坐标时会将classifier拼接在版本号后面,比如:hibernate-hikaricp-1.0.0-jdk8.jar

引入依赖

依赖查找网站:https://mvnrepository.com/

依赖的坐标示例:

<dependency>
  <groupId>org.hibernate</groupId>
  <artifactId>hibernate-hikaricp</artifactId>
  <version>1.0.0</version>
  <type>jar</type>
  <scope>test</scope>
  <optional>true</optional>
  <classifier></classifier>
</dependency>

optional

<optional>true</optional>

此时依赖传递失效,不会向上传递

如果A依赖于B,B依赖于C,B对C的依赖是optional,那么A就不会依赖于C。反之,如果没有optional,根据传递性依赖机制,A会依赖于C。

scope

maven在编译源代码的时候有一套classpath;在编译测试代码以及执行测试代码的时候,有一套classpath;运行项目的时候,有一套classpath;依赖范围就是用来控制依赖包与这三种classpath的关系的。

有如下参数可配置:

compile:默认,对编译、测试和运行的classpath都有效。一般都是用这种scope

test:仅仅对于运行测试代码的classpath有效,编译或者运行主代码的时候无效,仅仅测试代码需要用的依赖一般都会设置为这个范围,比如junit。一些测试框架,或者只有在测试代码中才会使用的一些依赖,会设置为test,这个的好处在于说,打包的时候这种test scope的依是不会放到最终的发布包里去的。减少发布包的体积。

provided:编译和测试的时候有效,但是在运行的时候无效,因为可能环境已经提供了,比如servlet-api,一般就是这个范围,在运行的时候,servlet容器会提供依赖。servlet-api是用来开发java web项目的,可能你在开发代码和执行单元测试的时候,需要在pom.xml里面声明这个servlet-api的依赖,因为要写代码和测试代码。但是最终打完包之后,放到tomcat容器里面去跑的时候,是不需要将这个servlet-api的依赖包打入发布包中的,因为tomcat容器本身就会给你提供servlet-api的包。

runtime:测试和运行classpath有效,但是编译代码时无效,比如jdbc的驱动实现类,比如mysql驱动。因为写代码的时候是基于javax.sql包下的标准接口去写代码的。然后在测试的时候需要用这个包,在实际运行的时候才需要用这个包的,但是编译的时候只要javax.sql接口就可以了,不需要mysql驱动类。一般我们声明mysql驱动的时候,不会设置为runtime,因为也许你开发代码的时候会用到mysql驱动特定的api接口,不仅仅只是用javax.sql。

system

使用上与provided相同,不同之处在于该依赖不从maven仓库中提取,而是从本地文件系统中提取,其会参照systemPath的属性进行提取依赖。

import

这个是maven2.0.9版本后出的属性,import只能在dependencyManagement的中使用,能解决maven单继承问题,import依赖关系实际上并不参与限制依赖关系的传递性。

依赖传递

比如A->B->C->X(1.0),A->D->X(2.0),A有两个传递性依赖X,不同的版本

此时就会依赖调解,就近原则,离A最近的选用,就是X的2.0版本

如果A->B->X(1.0)和A->D->X(2.0),

路径等长那么会选择第一声明原则,哪个依赖在pom.xml里先声明,就用哪个

排除传递依赖

<dependency>
  <groupId>org.hibernate</groupId>
  <artifactId>hibernate-hikaricp</artifactId>
  <version>1.0.0</version>
  <!-- 排除依赖 -->
  <exclusions>
    <exclusion>
      <artifactId>slf4j-log4j12</artifactId>
      <groupId>org.slf4j</groupId>
    </exclusion>
  </exclusions>
</dependency>

依赖冲突

原因

因为传递依赖的机制导致高版本的依赖没有生效。

解决方式

1、使用mvn dependency:tree 查看依赖路径,查看冲突的jar在哪里被引用了

2、然后确定其中一个高版本的jar

3、使用上文中的<exclusions>进行排除那个那个低版本的jar的传递依赖

Maven的仓库

几种仓库介绍

本地仓库

作用

对远程仓库的一个缓存仓库,使用到的包会从远程仓库拉取到本地仓库后进行使用。

配置

默认地址是 ~.m2/repository

可以通过setting.xml中的<localRepository>/User/c/maven/repository</localRepository>进行指定

在IDEA中也可以通过maven的设置中指定仓库地址

中央仓库

一般指maven中默认的<id>central</id><url>https://repo.maven.apache.org/maven2</url> 仓库,配置在(maven-model-builder-3.6.3jar:org.apache.maven.model.pom-4.0.0.xml),中央仓库还有其他的,比如jboss,但是很少有人使用。

私服

作用

企业中搭建自己的私服,自己来管理仓库

配置

配置在settrings.xml 或则 项目中的pom.xml中
有如下两种配置方式
<repositories></repositories>
通过profile配置仓库
<profile>
	<id>nexus</id>
  <repositories>
  </repositories>
</profile>

镜像仓库

作用

镜像配置的 repositorie,将仓库设置的url改为镜像配置的url进行操作。

配置

<mirrors>
	<mirror>
    <id>aliyun-maven</id>
    <mirrorOf>central</mirrorOf>
    <name>Nexus aliyun</name>
    <url>https://maven.aliyun.com/repository/public</url>
  </mirror>
</mirrors>

mirrorOf:指定需要镜像的仓库的id,多个仓库用 英文逗号(,)进行分割,central是maven默认的中央仓库地址。被镜像的仓库所配置的url将会失效。

仓库配置生效规则

配置的地方主要两种:settings文件 和 pom文件

主要分为两种配置方式:

直接配置仓库
<repositories></repositories>
通过profile配置仓库
<profile>
	<id>nexus</id>
  <repositories>
  </repositories>
</profile>

原则分为两种:

settings 优于 pom

profile 优于 repositories

情况:

settings:profile -> pom:profile -> setting:repositories -> pom:repositories

上传到仓库配置

maven会根据模块的版本号(pom文件中的<version>版本号</version>)中是否带有-SNAPSHOT来判断这个是快照版本还是正式版本.

pom.xml
<distributionManagement>
  <repository>
    <!-- 和 service.id 要匹配 -->
    <id>nexus-releases</id>
    <name>maven-releases</name>
    <url>http://192.168.1.15:8081/repository/maven-releases/</url>

    <layout>default</layout>
    <!--上传时指定版本,默认使用 version的版本-->
    <!--<uniqueVersion>1.0.0</uniqueVersion>-->
  </repository>
  <snapshotRepository>
    <id>nexus-snapshots</id>
    <name>maven-snapshots</name>
    <url>http://192.168.1.15:8081/repository/maven-snapshots/</url>
    <layout></layout>
    <uniqueVersion></uniqueVersion>
  </snapshotRepository>
</distributionManagement>

setting.xml
<servers>
  <server>
    <id>nexus-release</id>
    <username>admin</username>
    <password>admin</password>
  </server>
    <server>
    <id>nexus-snapshots</id>
    <username>admin</username>
    <password>admin</password>
  </server>
</servers>

Nexus私服搭建使用

下载安装

自行百度

企业级私服玩法

nexus中的几个核心仓库作用

常见的仓库如下图:

maven-releases:存放公司releases版本的包。

maven-snapshots:存放公司snapshots版本的包。

maven-central:代理中央仓库(国内一般代理aliyun镜像,aliyun镜像了maven中央仓库)

maven-public:对上面的几个仓库做分组,可以通过这个分组仓库拉取到分组内的所有仓库的包。

maven-public配置玩法:

权限体系

nexus默认有2个账号,admin 和 anonymous。

admin: 具有管理权限,可以拉取,上传,删除,管理nexus后台

anonymous:匿名用户,我们不提供账号密码的时候默认使用的就是这个匿名账号,该账号只能拉取。也可以在这设置中关闭匿名用户,让我们的私服的任何操作必须登录

权限管理

设置是否支持匿名账户

设置定时任务

配置仓库的的一些定时任务,比如:删除不完整的上传,删除未使用的快照等

Maven 生命周期

生命周期有三种:clean、default、site

生命周期中phase、plugin、goal的关系

完整的maven生命周期及默认配置:https://www.processon.com/view/link/6113f632e401fd5eeb87e600

生命周期有三种、每个生命周期都对应了固定的phase,有相应的执行顺序,plugin是对应到phase上的,goal是plugin上的一个个功能点,配置的时候会将某个plugin上的goal指定到对应的phase上,phase和plugin和goal都是多对多的关系。

plugin结合生命周期的配置方式

pom.xml
<build>
  <plugins>
    <plugin>
      <groupId>org.springframework.boot</groupId>
      <artifactId>spring-boot-maven-plugin</artifactId>
      <version>2.1.1.RELEASE</version>
      <!-- 指定goal -->
      <executions>
        <execution>
          <goals>
            <goal>repackage</goal>
          </goals>
        </execution>
      </executions>
      <!--参数,插件定义的-->
      <configuration>
        <skipTests>true</skipTests>
      </configuration>
    </plugin>
  </plugins>
</build>

使用plugin、goal的方式

mvn plugin:goal

示例:

mvn compiler:compile

单独执行plugin的goal 仅仅只会执行这一个goal,和生命周期无关

关于工程骨架 Archetype

自行百度

企业级使用案例

聚合功能实现多模块

自行百度

多模块依赖版本统一

父pom.xml
<properties>
		<hutool.version>2.4.1.10</hutool.version>
</properties>
<dependencyManagement>
  <dependencies>
    <dependency>
      <groupId>cn.hutool</groupId>
      <artifactId>hutool-all</artifactId>
      <version>${hutool.version}</version>
    </dependency>
  </dependencies>
</dependencyManagement>
<!--插件同理-->
<pluginManagement>
	<plugins>
		<plugin>
		</plugin>
	</plugins>
</pluginManagement>

子pom.xml
<dependencies>
  <dependency>
    <!--默认使用父pom中定义的版本号-->
    <groupId>cn.hutool</groupId>
    <artifactId>hutool-all</artifactId>
  </dependency>
</dependencies>
<plugins>
  <plugin>
  </plugin>
</plugins>

基于资源过滤+profile功能自动适配各个发布环境

pom.xml
<build>
	<resources>
    <resource>
      <directory>src/main/resources</directory>
      <excludes>
        <exclude>application*.properties</exclude>
      </excludes>
    </resource>
    <resource>
      <directory>src/main/resources</directory>
      <filtering>true</filtering>
      <includes>
        <include>application.properties</include>
        <include>application-${spring.profiles.active}.properties</include>
      </includes>
    </resource>
  </resources>
</build>
<profiles>
  <profile>
    <id>dev</id>
    <properties>
      <spring.profiles.active>dev</spring.profiles.active>
    </properties>
  </profile>
</profiles>

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值