写在前面

Maven,学习框架之前我们都会接触到的一个工具,感觉他的定位,似乎就跟git一样,只是方便我们开发?于是自然而然的,很多小猿对于Maven都只是停留在会用的阶段,利用他来构建,打包,引入jar包。

而实际上呢,Maven还有很多强大的地方,多模块开发,私服等等也是需要我们掌握的,在实际的开发中,往往是多模块共同开发,特别是我们之前提及的Dubbo分布式开发中,多模块开发是重中之重!

传统项目开发

导jar包

  • 既然是导jar包,我们是在本地windows开发,而实际项目是要放到linux服务器上,如果我们单纯把项目打成jar包丢上去,依赖文件也是jar包,但两个系统因为环境不一样,直接丢jar包(他不会重新编译运行的),得出来的结果可能就不一样

比如String的getByte方法,在两个系统上得到的结果是不一样的,如果没有重新编译运行,那最终也会有偏差

Maven概念

POM

Project Object Model

  • 把每个项目看成一个对象来进行管理

Maven作用

项目构建和管理

提供一套自动化构建项目的方法.并且通用,兼容性好,跨平台

  • 包括打包,编译,测试,运行等一套操作下来,让你在开发环境也可以方便进行测试等功能

构建是面向过程的,就是一些步骤,完成项目代码的编译,测试,运行,打包,部署等等。

maven支持的构建包括有:

1.清理, 把之前项目编译的东西删除掉,我新的编译代码做准备。

2.编译, 把程序源代码编译为执行代码, java-class文件

  • 批量的,maven可以同时把成千上百的文件编译为class。
  • javac 不一样,javac一次编译一个文件。

3.测试, maven可以执行测试程序代码,验证你的功能是否正确。

4.报告, 生成测试结果的文件, 测试通过没有。

5.打包, 把你的项目中所有的class文件,配置文件等所有资源放到一个压缩文件中。

  • 这个压缩文件就是项目的结果文件, 通常java程序,压缩文件是jar扩展名的。
  • 对于web应用,压缩文件扩展名是.war

6.安装, 把5中生成的文件jar,war安装到本地仓库供别的文件使用

7.部署, 把程序安装好可以执行。

这些在下边的生命周期其实刚刚好体现出来

依赖管理

  • 处理jar包冲突问题

统一开发结构--约定大于配置

即能进行配置的不要去编码指定,能事先约定规则的不要去进行配置。这样既减轻了劳动力,也能防止出错。

  • 实际上maven并没有强行要求约束我们项目的文件结构,而是因为他做得好,自然而然就变成一种通用的结构了

坐标

仓库

私服(下文中会有具体实例)

下载顺序??

先在本地仓库找,找不到就去私服找,如果私服没有,则会到中央仓库下载到私服并且发送到本地仓库

无论如何都还是最终会下到本地,区别只是从哪发送到本地而已?

  • 此处有点疑问,私服没有会去中央仓库下到私服吗?我下边配置了阿里云和私服,似乎私服没有的话是直接从阿里云直达下载到本地仓库,并不会通过私服?希望大佬可以指正一下!

图源 https://m.yisu.com/zixun/309916.html

镜像仓库配置

mirrorOf

对哪种仓库进行镜像

手工maven

Maven工程目录结构



构建命令

Maven构建命令使用mvn开头,后面加功能参数,可以一次执行多个命令,使用空格分隔

clean

把编译的去掉,target文件目录删除掉

install

把你的当前项目安装到本地仓库,成为一个jar包供别的项目引用里边的类

package

会先compile,然后再clean



依赖管理

依赖传递

依赖具有传递性,包括直接传递和间接传递。

直接传递:在当前项目中通过依赖配置建立的依赖关系(A使用B,A和B就是直接传递)

间接传递:如果A依赖B,而B依赖C,那么A和C之间就是间接传递

冲突原则

路径优先

在越浅层的优先级越高

声明优先

在同一层,先声明的比较高

在同一个pom中配置了相同资源的不同版本

后配置的覆盖前边的

可选依赖

排除依赖

①手动排除依赖,,且2可以直接把3整个依赖进来,再排除掉特定的



②借助idea插件排除依赖 -- Maven Helper

打开pom文件,下方就可以选择切换查看方式

右键选中你需要排除的 Exclude即可

③版本锁定--(待补充实例,拿Dubbo的吧)

Dubbo的GitHub文档中应用到了这点

<properties>
<spring-boot.version>2.3.0.RELEASE</spring-boot.version>
<dubbo.version>2.7.8</dubbo.version>
</properties> <dependencyManagement>
<dependencies>
<!-- Spring Boot -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${spring-boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency> <!-- Apache Dubbo -->
<dependency>
<groupId>org.apache.dubbo</groupId>
<artifactId>dubbo-dependencies-bom</artifactId>
<version>${dubbo.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency> </dependencies>
</dependencyManagement> <dependencies>
<!-- Dubbo Spring Boot Starter -->
<dependency>
<groupId>org.apache.dubbo</groupId>
<artifactId>dubbo-spring-boot-starter</artifactId>
<version>2.7.8</version>
</dependency>
</dependencies>

dependencyManagement

  • 通过它元素来管理jar包的版本,让子项目中直接引用依赖而不用列出版本号。Maven会沿着父子层次向上走,直到找到一个拥有元素的项目,然后它就会使用在这个dependencyManagement元素中指定的版本号。

管理通用性

  • 我们不需要给每个子项目都去声明版本了,只需要在最顶层父类中统一进行管理。

可扩展性

  • 如果某个子项目需要另外一个版本号时,只需要在dependencies中声明一个版本号即可。子类就会使用子类声明的版本号,不继承于父类版本号。

依赖范围

传递性(了解)

生命周期与插件



继承(SpringBoot就是一个很好的例子)

作用

通过继承可以实现在子工程中沿用父工程中的配置(与Java类似)

制作方式

在子工程中声明其父工程坐标与对应的位置

<!--定义该工程的父工程-->
<parent>
<groupId> </groupId>
<artifactId> </artifactId>
<version> </version>
<!--填写父工程的pom文件-->
<relativePath>父工程pom文件地址</relativePath>
</parent>

如SpringBoot中

<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.5.6</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>

在父工程中定义依赖管理

可以管理版本,解决子工程中依赖冲突问题(上文提及到的版本锁定)

<!--声明此处进行依赖管理-->
<dependencyManagement>
<!--具体的依赖-->
<dependencies>
<dependency>
<groupId> </groupId>
<artifactId> </artifactId>
<version> </version>
</dependency>
</dependencies>
</dependencyManagement>

继承依赖使用:在子工程中定义依赖关系,无需声明依赖版本,版本参照父工程中依赖的版本

<dependencies>
<dependency>
<groupId> </groupId>
<artifactId> </artifactId>
</dependency>
</dependencies>

聚合

  • 我们实际开发中,很多时候是多模块开发,会把业务单独抽离出来成为一个模块,比如Dao模块,Service模块

    • 那这个时候比如说Dao模块发生了变化,其他所有依赖Dao模块的模块怎么办呢,都得去更新吗?他自己知道吗?还是得我们自己去重新install重新依赖,有没有办法让他们同时更新而不是单独更新呢?--这就要用到我们的聚合

建立一个空模块

打包类型设置为pom

<packaging>pom</packaging>

聚合module

效果

私服仓库分类

  • 宿主仓库hosted:指的是我们公司或团队内部的包,并且 hosted 类型的仓库会分为 releases 和 snapshots 两个,前者是正式版,后者一般是开发测试版(快照版);

保存那些无法从中央仓库直接获取的资源,比如说我们自己研发的一些项目,或者一些第三方非开源项目比如oracle(要注意版权问题)

  • 代理仓库proxy:用来代理中央仓库,例如我们依赖的包在本地仓库没有,就会到私服获取,私服没有的话,会到中央仓库先把包下载到私服,然后再下载到本地仓库;
  • 仓库组group:把多个仓库组合起来,然后我们项目中只需要配置上这个类型的仓库地址,就可以把它里面组合的几个仓库都关联上.

**快速搭载Nexus私服

私服作用

有时候我们是多台机器开发,而我们要去引用别人机器上的模块jar包时,这个时候对方单纯install也只是发布到对方电脑上的本地仓库而已,我们还是访问不到.这个时候就需要一个中间商私服,来存放一些需要共享的资源

nexus下载安装

  • 首先要下载 nexus 搭载我们的私服
  • 下载完成后,修改etc中的启动端口(默认是8081)

  • 进入bin目录
  • vim nexus
  • 进入后直接 /run_as_user 查找到run_as_root 再按 i 进入编辑模式



把这一项改为false , 才可以用root用户开启nexus

  • 修改完成后 按ESC退出编辑模式进入命令模式 输入 :wq 保存退出即可
  • 最后 ./nexus start 启动
  • 访问你设置的端口号

账号默认是admin

初次登录会提示你去特定位置找密码



在该目录下寻找即可

之后可以修改默认密码

访问私服仓库(手动上传)--不推荐

  • 上方可以切换视图,左边是浏览仓库,右边的管理设置仓库,我们在管理这一层添加一个自己的仓库

这里我们创建一个宿主仓库

修改快照版/发行版

找到maven-public , 把我们刚创建的包含进去即可

去浏览页面找到我们的仓库,手动上传

idea环境上传

需要配置两个地方

  • 一个是本地仓库如何跟私服打交道 -- 对应默认的总setting文件
  • 一个是我们的工程要发布到私服具体哪个仓库 -- 对应当前项目pom文件里边的配置



上传jar认证配置

上传jar包需要认证,maven的认证是在.m2/settings.xml或自己的的maven里settings.xml中servers标签下配置的.

这里特别说明一下,servers配置的ID很关键,这个与你项目里面的distrubtionManagement下配置的仓库ID一致,否则会报审核未通过的错误。

<!--  配置访问服务器的权限-->
<server>
<id>nexus-Melo</id>
<username>admin</username>
<password>admin</password>
</server>
<server>
<id>Melo-Release</id>
<username>admin</username>
<password>admin</password>
</server>
<server>
<id>Melo-Snapshots</id>
<username>admin</username>
<password>admin</password>
</server>

这里的id对应了setting.xml里配置的server.id信息name任取

<!--    私服发布管理-->
<distributionManagement>
<repository>
<!-- id要跟setting中配置访问时的id一致-->
<id>Melo-Release</id>
<!-- 仓库地址 去nexus网站找到仓库复制url即可 -->
<url>http://ip地址:端口/repository/Melo-Release/</url>
</repository>
<snapshotRepository>
<id>Melo-Snapshots</id>
<url>http://ip地址:端口/repository/Melo-Snapshot/</url>
</snapshotRepository>
</distributionManagement>

上传效果

idea环境从私服获取(同时使用阿里云镜像+私服)

  • 配置全局setting.xml,我们所有项目就都会去私服找了

建议使用自带的maven-public仓库组 , 然后把我们自己创建的仓库包含进去

注意不要把proxy类的仓库包含进我们的group!这样我们配置的阿里云镜像就失效了

除非自己去手动改proxy代理的仓库地址,但个人感觉不太推荐,具体见后文"另外的实现方式"

配置server--访问服务器的权限

包含拉取和上传的两部分配置,两部分都需要权限

<!--  配置访问服务器的权限-->
<!--第一个id要和下面的mirror中的id一致,代表拉取时也需要进行身份校验-->
<server>
<id>nexus-Melo</id>
<username>你的私服账号</username>
<password>你的私服密码</password>
</server>
<!-- 下边是我们上传时的访问配置,id对应你上传时<distributionManagement>中写的id-->
<server>
<id>Melo-Release</id>
<username>你的私服账号</username>
<password>你的私服密码</password>
</server>
<server>
<id>Melo-Snapshots</id>
<username>你的私服账号</username>
<password>你的私服密码</password>
</server>

配置mirror

<!--    阿里云私服,拿中央仓库-->
<mirror>
<id>alimaven</id>
<name>aliyun maven</name>
<url>http://maven.aliyun.com/nexus/content/groups/public/</url>
<!-- 访问中央仓库才使用阿里云镜像-->
<mirrorOf>central</mirrorOf>
</mirror>
<!-- 自己的maven私服-->
<mirror>
<id>nexus-Melo</id>
<!--镜像名称 -->
<name>nexus-Melo</name> <!--镜像除了中央仓库以外的仓库(本地有的话还是优先本地,没有再去私服找,私服没有的话会先通过阿里云下载到私服,再发送到本地)-->
<mirrorOf>!central</mirrorOf>
<!--该镜像的URL。构建系统会优先考虑使用该URL,而非使用默认的服务器URL。
选择你用哪个私服仓库来作为镜像,建议选择自带的maven-public,具体看上边 -->
<url>http://ip地址:端口/repository/maven-public/</url>
</mirror>

扩展--mirrorOf

*表示所有 !表示非

,!repo1 : 在除了repo1的仓库中寻找

external:
: 刚好跟上边的 !internal.repo,* 相反

扩展--mirror**

  • 默认情况下配置多个mirror的情况下,只有第一个生效。

    • 无法连接的时候,才会去找后一个;而我们想要的效果是:当某个jar包在第一个mirror中不存在的时候,maven会去第二个mirror中查询下载,但是maven不会这样做!

正确的操作是在profiles节点下配置多个profile,而且配置之后要激活!!!!

配置profile

<!--      阿里云-->
<profile>
<id>aliyun</id>
<repositories>
<repository>
<id>aliyun</id>
<url>http://maven.aliyun.com/nexus/content/groups/public/</url>
<releases>
<enabled>true</enabled>
</releases>
<snapshots>
<enabled>true</enabled>
<updatePolicy>always</updatePolicy>
</snapshots>
</repository>
</repositories>
</profile> <!-- 自己的私服-->
<profile>
<!-- 注意这个id,下边激活的时候会用到,要一一对应-->
<id>nexus-pr</id>
<!-- 远程仓库列表 -->
<repositories>
<repository>
<!-- 上边要拉取的仓库id-->
<id>nexus-Melo</id>
<name>nexus-Melo</name>
<!-- 虚拟的URL形式,指向镜像的URL-->
<url>http://ip地址:端口/repository/maven-public/</url>
<layout>default</layout>
<!-- 表示可以从这个仓库下载releases版本的构件-->
<releases>
<enabled>true</enabled>
</releases>
<!-- 表示可以从这个仓库下载snapshot版本的构件 -->
<snapshots>
<enabled>true</enabled>
</snapshots>
</repository>
</repositories>
<!-- 暂时还没有自定义插件的需求 -->
<!-- 插件仓库列表 -->
<!-- <pluginRepositories>-->
<!-- <pluginRepository>-->
<!-- &lt;!&ndash; 上边要拉取的仓库id&ndash;&gt;-->
<!-- <id>nexus-Melo</id>-->
<!-- <name>nexus-Melo</name>-->
<!-- <url>http://114.132.235.87:9001/repository/maven-public/</url>-->
<!-- <layout>default</layout>-->
<!-- <snapshots>-->
<!-- <enabled>true</enabled>-->
<!-- </snapshots>-->
<!-- <releases>-->
<!-- <enabled>true</enabled>-->
<!-- </releases>-->
<!-- </pluginRepository>-->
<!-- </pluginRepositories>-->
</profile>

激活profile!!

				<!--对应上边profile定义的id!!!-->
<!-- 激活阿里云-->
<activeProfile>aliyun</activeProfile>
<!-- 激活nexus-->
<activeProfile>nexus-pr</activeProfile>
<activeProfile>jdk-1.8</activeProfile>

实现阿里云与私服共存的效果

那些中央仓库有的文件,就会走阿里云镜像去下载,如果是我们自定义的jar包(中央仓库没有的),就会走我们的私服去下载!

另外的实现方式

  • 其实我们也可以直接在私服创建一个proxy仓库,让他代理阿里云镜像就好了,但是这样其实也有个问题,就是proxy仓库本身是不允许我们自定义上传组件的,所以综合考虑的话还是上边自行配置的方法好一点

写在最后

  • maven这一块,具体的聚合继承实例,等到真正运用上了分布式开发的时候,应该会有所渗透。而私服的运用,在多台机器上是十分重要的!

Maven还停留在导jar包?快来探索Nexus私服的新世界的更多相关文章

  1. 如何将第三方jar包上传到Nexus私服

    首先登陆私服服务器         以动力威视私服为例:          自己搭建的私服地址:http://192.168.1.5:8081/nexus/index.html#view-reposi ...

  2. Intellij Idea系列之导Jar包与编写单元测试(二)

     Intellij Idea系列之导Jar包与编写单元测试(二) 一.初衷 对于很多的初学者来说,Intellij如何导入jar包感到很迷惑,甚至在网上搜过相关文章之后还是云里雾里,本博客通过图文并茂 ...

  3. 说点手动导jar包的细节Referenced Libraries

    对于Referenced Libraries 若是手动,新建好Scala项目工程,这里取名为ScalaInAction 得需将Scala 2.11.8自带的,换成2.10.*版本 在其上,点击右键,B ...

  4. eclipse导出maven工程的可执行jar包

    一.eclipse导出maven工程的可执行jar包 建立两个maven工程 ZKServer 和ZKClient 注意:用maven进行开发管理的话,默认的打出来的jar包是不能运行的,需要在pom ...

  5. maven向本地仓库导入jar包(处理官网没有的jar包)

    对于官网没有的jar包,maven向本地仓库导入jar包用如下命令 mvn install:install-file -DgroupId=包名 -DartifactId=项目名 -Dversion=版 ...

  6. 【转】maven导出项目依赖的jar包

    本文转自:http://my.oschina.net/cloudcoder/blog/212648 一.导出到默认目录 targed/dependency 从Maven项目中导出项目依赖的jar包:进 ...

  7. Maven导出Project依赖的jar包

    Maven导出Project依赖的jar包 从Maven仓库中导出jar包: mvn dependency:copy-dependencies 会导出到Project的targed/dependenc ...

  8. [Maven]Maven构建可执行的jar包(包含依赖jar包)

    ----------------------------------------------------------------- 原创博文,如需转载请注明出处! 博主:疲惫的豆豆 链接:http:/ ...

  9. Maven 生成可执行的jar包

    maven 默认打包生成的 jar 包是不能够直接运行的,因为带有 main 方法的类信息不会添加到 manifest 中,即打开 jar 文件中的 META-INF/MANIFEST.MF 文件,将 ...

随机推荐

  1. k8s 部署elasticsearch报 max virtual memory areas vm.max_map_count [65530] is too low, increase to at least [262144]

    1.由于登不上云的节点 不采用修改节点配置的方式 修改部署的stateful 加上 initContainers 它和 containers 同一层级的 initContainers: - name: ...

  2. 383 day10缓冲流、转换流、序列化流

    day10[缓冲流.转换流.序列化流] 主要内容 缓冲流 转换流 序列化流 打印流 教学目标 [ ] 能够使用字节缓冲流读取数据到程序 [ ] 能够使用字节缓冲流写出数据到文件 [ ] 能够明确字符缓 ...

  3. 一文彻底搞懂Hive的数据存储与压缩

    目录 行存储与列存储 行存储的特点 列存储的特点 常见的数据格式 TextFile SequenceFile RCfile ORCfile 格式 数据访问 Parquet 测试 准备测试数据 存储空间 ...

  4. 建立 F103C8T6 HAL库 Makefile FreeRTOS 工程

    F103C8T6 HAL库 Makefile FreeRTOS 工程模板 环境 该工程的开发平台为 ARM-GCC 工具链和 Make > arm-none-eabi-gcc -v gcc ve ...

  5. 用java代码遍历excel文件并回显

    今天需要完成282个指标,分析后发现好多都是可复用的字段和方法,生成的dao类也是很多重复的代码,所以写下了简单的自动化遍历excel的test方法, excel业务逻辑如下,用了 HSSFSheet ...

  6. 在PHP中操作文件的扩展属性

    在操作系统的文件中,还存在着一种我们可以自己定义的文件属性.这些属性不是保存在文件内容中,也不是直接可以通过 ls -al 所能看到的内容.它们可以将一个键值对信息永久得关联到文件上,一般现在的 Li ...

  7. 根据类拼凑成url参数

    /// <summary>        /// 根据类拼凑成url参数        /// </summary>        /// <typeparam name ...

  8. gitlab与git命令

    gitlab安装目录 /etc/gitlab#配置文件目录 /run/gitlab#运行pid目录 /opt/gitlab#安装目录 /var/opt/gitlab#数据目录 /var/log/git ...

  9. css定位,class属性之间有空格与无空格的区别

    中间有空格的情况 是选择到.class1类下的.class2类子节点,即.class2类的节点要是.class1类子节点 <style> .class1 { color: black; } ...

  10. requestAnimationFrame 切换页面问题

    requestAnimationFrame 切换页面时, 之前定时的内容还会继续执行. 所以 要注意处理动画函数内容,否则会出现死循环. 遇到的问题: 我在两个页面都有使用 requestAnimat ...