常春藤怎么样:发表作品?

时间:2008-12-09 16:18:25

标签: java ant build-process build-automation ivy

我完全不知道蚂蚁任务常春藤:发布应该如何运作。

我希望我做正常的构建,创建一堆jar文件,然后我会将这些jar推送到(本地)存储库。

如何指定从哪里检索已构建的jar,以及它们将如何最终存储在存储库中?

更新

<target name="publish-local" description="--> Publish Local">
    <ivy:retrieve />
    <ivy:publish resolver="local" pubrevision="${release.version}" status="release" update="true" overwrite="true">
        <artifacts pattern="${dist.dir}/[organisation]-[module].[ext]" />
    </ivy:publish>
</target>

这实际上有效,我之前没有包含检索。

但是我仍然有一些问题,假设我想发布3个罐子,openscada-utils.jar,openscada-utils-sources.jar和openscada-utils-javadocs.jar作为openscada-utils-0.9.2.jar, openscada-utils-0.9.2-sources.jar和openscada-utils-0.9.2-javadocs.jar

我不完全清楚,实际的名字是如何组合的,以及我可以指定他们应该得到哪些名字的地方。 (使用上面的片段,jar总是只调用utils.jar)。

更新1:

我让它工作(有点),但它仍然感觉不对。不知何故,所有教程都关注第三方项目的依赖关系,但对我来说同样重要的一点是处理项目特定的依赖关系。

我有一堆子项目,它们以各种方式相互依赖。考虑常春藤:发布我不清楚如何开始。

  1. 如何处理第一个版本?我有一个共同的版本号用于所有子项目,以表明它们属于一起(假设为0.9)。因此第一次修订应该是0.9.0,但到目前为止,我的项目中没有任何内容存在于我的存储库中。如何让Ivy分配此修订号。

  2. 在开发过程中,我想再次发布构建的文件,而不更改目前的版本号。

  3. 如果我完成了我的工作,我想将其推送到共享存储库(并将修订版号从0.9.0增加到0.9.1),建议的方法是什么?

  4. 对于实际版本,我想制作具有依赖关系的发行版,但不知道我想我可以使用不同的配置。我怎样才能利用这个优势呢?

4 个答案:

答案 0 :(得分:10)

您需要指定“解析器”。类似的东西:

<ivy:publish resolver="local" pubrevision="1.0"/>

它受模式控制。这个page很好地涵盖了它。看起来你想要你的:

<artifacts pattern="${dist.dir}/[organisation]-[module]-[revision]-[type].[ext]" />

您需要在ivy.xml文件中将三个罐子识别为工件。像这样:

<publications>
    <artifact name="utils"/>
    <artifact name="utils" type="source"/>
    <artifact name="utils" type="javadocs"/>
</publications>

答案 1 :(得分:4)

首先,您需要一个ivy.xml文件。

<ivy-module version="2.0">
    <info organisation="com.example.code" module="MyProject"
         revision="${project.revision}"/>
    <configurations>
        <conf name="runtime" description="" />
        ... other config elements here...
    </configurations>

    <publications defaultconf="runtime">
        <artifact name="MyProject" type="jar" ext="jar" conf="runtime" />
    </publications>

    <dependencies>
        ...
    </dependencies>
</ivy-module>

ivy.xml中的info元素和publication元素允许您 跳过build.xml中常春藤元素的各种属性。

请注意ivy.xml中的$ {project.revision}。该物业是有价值的 在build.xml中,但这看起来很好用。然后可以进行修订 容易拥有所需的任何价值(例如,夜间构建与本地构建)。

以下是如何设置build.xml文件的示例

<property name="project.revision" value="1.0.0"/>

...

<target name="ivy">
    <ivy:resolve />

    <!-- Possible ivy:report, ivy:retrieve and other
    elements for managing your dependencies go here -->

    <ivy:deliver conf="*(public)"/> 
</target>

<target name="publish" depends="clean, ivy, jar">
    <ivy:publish resolver="local">
        <!-- possible artifacts elements if your artifacts
        are not in standard location -->
    </ivy:publish>
</target>

...

答案 2 :(得分:2)

您希望首先运行<ivy:deliver/>任务。这将创建一个可供Ivy存储库使用的ivy.xml文件。

使用<ivy:publish>时,通过在resolver参数中指定要指定要发布到的存储库。这需要匹配ivy.settings.xml文件中的解析程序名称。

您没有真正指定工件,而是指定要发布工件的模式。您可以通过<artifacts>任务上的<ivy:publish>子任务指定此项。例如,如果您像我们一样在${basedir}/target/archive目录下构建所有内容,则可以将其指定为:

<ivy:publish resolver="public">
   <artifacts path="target/archive/[artifact].[ext]"/>
</ivy:publish>

如果要更改文件的修订号,可以使用<ivy:publish>任务的 pubrevision 参数。这不会更新ivy.xml,但会将您的罐子/战争发布到正确的版本。我更喜欢使用<ivy:deliver>任务的 pubrevision 参数,并让它创建正确的ivy.xml文件。然后,<ivy:publish>将使用我的ivy.xml文件中的修订版。

您无需执行<ivy:retrieve>。毕竟,你正在运行一个构建来创建新的jar,它们应该在你的构建中是SOMEWHERE。否则,如果你没有创建一个jar或战争你想要发布到你的Ivy存储库中的是什么?并且,您当然不希望检索已经存在于Ivy存储库中的内容,只是为了重新发布它。


我的理念一直是发布是一项CM任务,不应该作为构建过程的一部分来完成。因此,我们不使用<ivy:deliver><ivy:publish>

我们使用Artifactory作为我们的Ivy存储库(以及我们的Maven存储库)。我们使用Jenkins作为我们的持续构建服务器。

我所做的是让开发人员通过pom.xml任务从ivy.xml文件中生成<ivy:makepom>文件。这个和构建jar / wars在Jenkins中保存为归档工件。

当我们对特定构建感到满意并希望它在我们的公共存储库中时,我使用Jenkin的Promote Build任务将其pom.xml的特定jar / war推广到我们的Artifactory存储库。我们使用mvn deploy:deploy-file任务来完成此任务。

答案 3 :(得分:0)

了解常春藤正在做什么很重要。它不仅仅是将工件罐复制到常春藤存储库中 - 它还生成相关的“.ivy.xml”文件,这些文件指定了每个工件的所有依赖项。

在幕后,ivy:retrieve任务实际上也触发ivy:resolve。当ivy:resolve发生时,文件将写入您的本地常春藤缓存(位于.ivy中的user.home文件夹中),该缓存指定解决方案的发生方式(完成解决方案需要哪些模块的修订版) 。)遇到ivy:publish时,将从缓存中检索该解析记录,并用于为工件生成ivy.xml。

我在执行此操作时发现的最大缺陷是要求ivy:resolveivy:publish任务在由ant执行时由同一个类加载器加载。确保发生这种情况的最简单方法是在taskdef任务中使用loaderRef。例如(注意匹配的loaderRef标签):

<taskdef name="ivy-retrieve" 
     classname="org.apache.ivy.ant.IvyRetrieve" 
     classpathref="ivy.lib" 
     loaderRef="ivy.loader"/>
<taskdef name="ivy-publish" 
     classname="org.apache.ivy.ant.IvyPublish" 
     classpathref="ivy.lib" 
     loaderRef="ivy.loader"/>