通过示例向本地Ivy缓存发布和从本地Ivy缓存解析

  • 本文关键字:缓存 Ivy java maven ant ivy
  • 更新时间 :
  • 英文 :


我认为这里最令人惊讶的是,这个功能是默认嵌入到Maven和Gradle中的,然而,在Ant/Ivy环境中却没有它存在的痕迹(你自己看看吧!)


我继承了一套使用Ant/Ivy作为构建/依赖系统的JVM组件。这些组件之间有很多依赖关系,这意味着对其中一个组件进行更改通常会产生连锁反应,要求您更新Ivy依赖关系并发布上游依赖关系的新版本。

维护这些项目的旧团队通过将快照jar发布到快照仓库来处理本地开发。我想用一个新的范例来取代这个范例,即快照从本地Ivy缓存发布到/解析。

我能够找到这个非常相似的问题,但发现答案有点缺乏细节(特别是一个完全拼接在一起的代码片段),部分原因是问题缺乏任何特定的代码示例。所以我在这里创建了一个SSCCE,并推送了2个GitHub repos:

  • fizzbuzz-model,定义数据模型(一些无意义的pojo)的Java库
  • fizzbuzz-app,一个简单的可执行jar, 依赖于 fizzbuzz-model作为依赖项

我在这里寻找的是确切的(即实际代码,而不是伪代码)更改(可能是build.xml, ivy.xmlivy-settings.xml,或全部三个!),这将允许我使用以下本地开发/测试周期:

  1. 我对fizzbuz-model进行更改,并将更改本地发布到Ivy缓存,最好是作为快照版本(如1.0.0-SNAPSHOT或类似)
  2. fizzbuzz-app根目录中,我运行ant resolve,它从缓存的快照
  3. 中提取这些更改现在我可以在fizzbuzz-app 中使用这些更改

虽然不是一个硬性要求,但我理想地希望而不是必须手动管理版本号。也就是说,当我在本地发布fizzbuzz-model时,它用相同的版本(再次,像fizzbuz-model-1.0.0-SNAPSHOT.jar一样)覆盖当前二进制文件,而不是将构建号增加到fizzbuzz-model-1.0.1-SNAPSHOT.jar或类似的版本)。这样,在本地测试时,我所要做的就是发布fizzbuzz-model并解析fizzbuzz-app

目前,当我发布fizzbuzz-model,我得到以下错误:

/Users/myuser/workspace/fizzbuzz-model/build.xml:52: impossible to publish artifacts for hotmeatballsoup#fizzbuzz-model;1.0: java.io.IOException: missing artifact hotmeatballsoup#fizzbuzz-model;1.0.0-SNAPSHOT!fizzbuzz-model.pom
    at org.apache.ivy.core.publish.PublishEngine.publish(PublishEngine.java:225)
    at org.apache.ivy.core.publish.PublishEngine.publish(PublishEngine.java:172)

要在本地复制,克隆这两个项目并遵循它们的readme,从fizzbuzz-model开始。谁能发现我在哪里走错了?请随意在这里回答和/或提交PR,无论您喜欢哪一种!和谢谢!

该错误指示ivy无法在本地构建工作区中找到要发布的文件。这不是快照的问题。

问题在这里:

<ivy:publish resolver="local" pubrevision="1.0.0-SNAPSHOT" >
  <artifacts pattern="dist/[artifact]-[revision].[ext]" />
</ivy:publish>

您在模式中包含了一个"修订",但不幸的是,您在本地创建的jar与此命名约定不匹配。它既没有修改,又有一个错别字(应该是"fizzbuzz",而不是"fizzbuzz"):

<target name="dist" depends="clean,compile">
  <jar jarfile="dist/fizzbuz-model.jar" basedir="build/main" />
</target>

我预测更多的问题,因为您正在尝试配置ivy来模拟Maven存储快照修订的方式。这需要Maven从未正式记录的额外元数据文件。我强烈建议将已发布的文件推送到Maven存储库管理器,以获得格式正确的SNAPSHOT存储。

下面是从ivy

向Maven仓库发布工件的示例
  • 使用IVY将SNAPSHOT工件发布到Maven -有什么魔力?
  • https://support.sonatype.com/hc/en-us/articles/213465388-How-do-I-configure-my-Ivy-build-to-deploy-artifacts-to-Nexus-

<标题>建议解决方案

我已经按照请求提交了Pull请求,并提出了关于如何优先使用本地ivy存储库而不是快照版本的建议:

  • fizzbuzz-model - (Pull request)
  • fizzbuzz-app - (Pull request)

总而言之,模型在每次新构建时都会发布一个新的修订

<target name="publish" depends="clean,dist">
    <!-- Determine build number from previously published revisions -->
    <ivy:buildnumber resolver="local" organisation="${ivy.organisation}" module="${ivy.module}" revision="${target.release}"/>
    <!-- Resolve ivy dependencies and create a Maven POM file -->
    <ivy:deliver deliverpattern="dist/ivy.xml" pubrevision="${ivy.new.revision}" status="release"/>
    <ivy:makepom ivyfile="dist/ivy.xml" pomfile="dist/fizzbuzz-model.pom" />
    <!-- Publish the local repo. Defaults to ~/.ivy2/local -->
    <ivy:publish resolver="local" pubrevision="${ivy.new.revision}" >
        <artifacts pattern="dist/[artifact].[ext]" />
    </ivy:publish>
</target>

它在应用代码中被用作动态依赖项,总是检索其他模块的最新发布版本。

<dependencies>
    <dependency org="hotmeatballsoup" name="fizzbuzz-model" rev="latest.integration" conf="compile->default" />
</dependencies>

指出:

  • 作为奖励,POM文件也正在生成,严格来说,除非您将工件推送到Maven仓库,否则它是不必要的。

<标题> 的背景像ivy这样的依赖管理器出现在Maven普遍流行之前(我记得Maven 1.0被普遍讨厌的时候),所以ivy没有完全实现Maven的工作流程也就不足为奇了。

Maven一直是一个非常固执己见的工具。令人困惑的是,它支持两种发布工件的方法。作为一个释放或快照。在我看来,这是在尝试使用Maven进行持续部署时造成最大摩擦的原因,在持续部署中,应该考虑发布所有的版本。但不可否认的是,Maven是分发所有基于Java的二进制文件的通用方式。Maven存储库可以作为一个集成点,支持多种构建技术,Maven、Gradle或ANT/Ivy。

因此,首先需要接受的是,快照开发工作流对于Maven来说是非常特殊的,并且据我所知,还没有被任何其他存储库格式复制。

在其他存储库中,一个版本的版本号总是唯一的。这适用于官方版本、候选版本或开发版本。另一方面,Maven快照永远不会完成。这是什么意思呢?如果我今天基于版本"1.0-SNAPSHOT"进行构建,那么明天的依赖关系可能会完全不同。这是因为每个新的快照构建将在幕后创建一个新的时间戳工件,以覆盖先前存储的二进制文件。

Ivy有不同的机制来支持开发构建(不同并不意味着更好)。可以依赖于开发中的最新版本,但这总是在构建时显式地解决。当将工件发布到ivy存储库时,方便的交付任务能够创建完全解析的ivy文件。对于所使用的依赖的版本,从来没有任何歧义。

所以在结论中,首先要考虑是否真的需要支持快照工作流。除非您打算使用Maven与其他团队集成,否则强迫ivy遵循它不支持的工作流是不明智的。

相关内容

  • 没有找到相关文章