在多模块环境中管理 Unmavenized 工件

一则或许对你有用的小广告

欢迎加入小哈的星球 ,你将获得:专属的项目实战 / 1v1 提问 / Java 学习路线 / 学习打卡 / 每月赠书 / 社群讨论

  • 新项目:《从零手撸:仿小红书(微服务架构)》 正在持续爆肝中,基于 Spring Cloud Alibaba + Spring Boot 3.x + JDK 17...点击查看项目介绍 ;
  • 《从零手撸:前后端分离博客项目(全栈开发)》 2 期已完结,演示链接: http://116.62.199.48/ ;

截止目前, 星球 内专栏累计输出 63w+ 字,讲解图 2808+ 张,还在持续爆肝中.. 后续还会上新更多项目,目标是将 Java 领域典型的项目都整一波,如秒杀系统, 在线商城, IM 即时通讯,权限管理,Spring Cloud Alibaba 微服务等等,已有 2200+ 小伙伴加入学习 ,欢迎点击围观

Maven 的声明性行为强制用户使用托管工件,不鼓励使用非托管/外部/非 Mavenized 工件/罐子。

有几种解决方法可以解决此问题。下面描述了一些黑客攻击。

方法 1:使用“系统”范围

Maven 提供称为“系统”的范围,它需要绝对路径。但是使用绝对路径会使构建用户特定,这在自动化工具中不应该发生。使用 ${basedir} 变量可以避免这种情况。该变量提供当前模块的绝对路径,因此相对于当前模块放置的 jar 可以使用 ${basedir} 变量进行相对访问。

  • 创建一个文件夹(比如 lib)并将外部 jar 保存到 lib 文件夹中。
  • 可以如下所示访问这些罐子。

<依赖关系>

<groupId>com.bala</groupId>

<artifactId>测试工件</artifactId>

<版本>1.0</版本>

<范围>系统</范围>

<systemPath>${basedir}/lib/test-artifact.jar</systemPath>

</依赖>

优点 :易于实施

缺点 :在模块化项目的情况下,如果在多个模块中使用相同的 jar,则应在所有这些模块中复制该 jar。 (你可能会想为什么我们不能把它放在父 pom 中,但是子模块不能访问父的绝对路径。Maven 3+ 不支持从子模块访问父的属性。)


方法 2:使用基于文件的存储库

  • 创建一个本地存储库(如果您使用版本控制,请说 lib 并将此 lib 与外部 jar 一起提交)。
  • 识别所有外部 jar 并使用以下命令安装它们。

mvn install:install-file -Dfile=<path-to-file> -DgroupId=<custom-group-id> -DartifactId=<custom-artifact-id> -Dversion=<custom-version> -DlocalRepositoryPath=<path-到本地回购文件夹>

  • 在您的 pom 中指定基于文件的本地存储库,如下所示。

<存储库>

<存储库>

<id>自定义仓库 ID</id>

<name>自定义仓库名称</name>

<url>文件:${basedir}/lib</url>

</存储库>

</存储库>

  • 现在可以在依赖项部分的最小 pom 的帮助下使用外部依赖项。

<依赖关系>

<groupId>自定义组id</groupId>

<artifactId>自定义工件 ID</artifactId>

<version>自定义版本</version>

</依赖>

优点 :比使用系统范围更好。

缺点 :在模块化项目的情况下,如果在多个模块中使用相同的 jar,则应将此 jar 安装在所有模块的 repo 中。 (你可能会想为什么我们不能把它放在父 pom 中,但是子模块不能访问父的绝对路径。Maven 3+ 不支持从子模块访问父的属性。)。此外,此方法添加了不必要的文件并提交到版本控制的存储库,这是不可取的。

方法三(推荐):

方法 2 可以通过使用 maven 的插件功能来增强。在前面的方法中,外部 jar 被安装到基于文件的 repo 中,该 repo 将存在于版本控制的 repo 中。相反,如果您可以在用户运行 clean 或 compile 后立即将 jar 安装到用户的本地存储库中,那么将使用最小的 pom 访问它。我建议按照以下步骤进行。

  • 在当前项目中创建一个文件夹(比如 lib),并将所有 jar 保存到该文件夹​​中。在模块化项目的情况下,创建一个模块,比如 external-jar-installer 并将 lib 文件夹与 jars 一起复制到模块中。确保签入 lib 文件夹。
  • 现在使用 maven 安装插件并在清理阶段配置所有 jar,如下所示。


<构建>
<插件>
<插件>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven 安装插件</artifactId>
<版本>2.4</版本/>
<处决>
<执行>
<id>自定义唯一标识</id>
<phase>清理</phase>
<目标>
<goal>安装文件</goal>
</目标>
<配置>
<文件>${basedir}/lib/your-artifact.jar</文件>
<groupId>自定义组id</groupId>
<artifactId>自定义工件 ID</artifactId>
<version>自定义版本</version>
</配置>
</执行>
<执行>
<id>自定义唯一 ID2</id>
<phase>清理</phase>
<目标>
<goal>安装文件</goal>
</目标>
<配置>
<文件>${basedir}/lib/your-artifact2.jar</文件>
<groupId>自定义组id2</groupId>
<artifactId>自定义工件 id2</artifactId>
<版本>自定义版本2</版本>
</配置>
</执行>
</执行>
</插件>
</插件>
</构建>

  • 一旦我们运行 mvn clean,所有的 jar 都会从 lib 文件夹中获取并安装到用户的本地 repo 中。因此,最小 pom 对执行其余 mvn 命令的用户有效。

优点: 这将是一种更简洁的方式,即使在模块化项目的情况下也是如此。可以专门分配一个模块来安装这些jar和插件。其余模块将忽略外部 jar,它们将像从存储库中获取一样使用它们。


相关文章