How does ivy:publish work?

25,141

Solution 1

You need to specify the "resolver". Something like:

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

It's controlled by the pattern. This page covers it pretty well. It looks like you want yours to be:

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

And you'll need to identify the three jars as artifacts in the ivy.xml file. Something like this:

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

Solution 2

First you need an ivy.xml file.

<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>

The info element and publications elements in ivy.xml allow you to skip various attributes on the ivy elements in build.xml.

Note the ${project.revision} in ivy.xml. The property is given value in build.xml, but this seems to work nicely. The revision can then easily have whatever value is required (eg. nightly builds vs. local builds).

Here is a sample how you could set up your build.xml file

<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>

...

Solution 3

You're suppose to run the <ivy:deliver/> task first. This creates an ivy.xml file that can be used by the Ivy repository.

When you use <ivy:publish> you specify which repository you want to publish to by specifying it in the resolver parameter. This needs to match the resolver name in your ivy.settings.xml file.

You don't really specify the artifacts, but a pattern where to find the artifacts to publish. You specify this via the <artifacts> subtask on the <ivy:publish> task. For example, if you build everything under the ${basedir}/target/archive directory like we do, you can specify it as this:

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

If you want to change the revision number of your file, you can use the pubrevision parameter of the <ivy:publish> task. This doesn't update the ivy.xml, but will publish your jars/wars to the correct revision. I prefer to use the pubrevision parameter of the <ivy:deliver> task and let it create the correct ivy.xml file anyway. Then, <ivy:publish> will use the revision in my ivy.xml file.

You don't need to do <ivy:retrieve>. After all, you're running a build to create new jars, and they should be SOMEWHERE in your build. Otherwise, if you're not creating a jar or war what are you trying to publish into your Ivy repository? And, you certainly don't want to retrieve something already in your Ivy repository just to republish it.


My philosophy has always been that publishing is a CM task and shouldn't be done as part of the build procedure. Thus, we don't use <ivy:deliver> or <ivy:publish>.

We use Artifactory as our Ivy repository (and our Maven repository). We use Jenkins as our continuous build server.

What I do is have the developers make a pom.xml file out of their ivy.xml file via the <ivy:makepom> task. This and the build jars/wars are saved as archived artifacts in Jenkins.

When we are happy with a particular build and want it in our public repository, I use Jenkin's Promote Build task to promote a particular jar/war with its pom.xml to our Artifactory repository. We use the mvn deploy:deploy-file task to do that.

Share:
25,141

Related videos on Youtube

Mauli
Author by

Mauli

My favourite language is Python, although for work I have to program in Java (Spring, Hibernate, OpenSCADA).

Updated on July 09, 2022

Comments

  • Mauli
    Mauli almost 2 years

    I'm completely at loss how the ant task ivy:publish is supposed to work.

    I would expect that I do my normal build, which creates a bunch of jar files, then I would push those jars to the (local) repository.

    How can I specify from where to retrieve the built jars, and how would those end up in the repository?

    Update:

    <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>
    

    this actually works, I didn't include the retrieve before.

    But I still have some problems, suppose I want to publish 3 jars, openscada-utils.jar, openscada-utils-sources.jar and openscada-utils-javadocs.jar as openscada-utils-0.9.2.jar, openscada-utils-0.9.2-sources.jar and openscada-utils-0.9.2-javadocs.jar

    It isn't entirely clear to me, how the actual names are assembled, and where I can specify which names they should get. (Using the fragment above, the jars are always called only utils.jar).

    Update 1:

    I got it to work (a bit), but it still doesn't feel right. Somehow all tutorials focus on dependencies from 3rd party projects, but an equally important point for me is to handle project specific dependencies.

    I have a bunch of sub projects which depend on each other in various ways. Considering ivy:publish it is not clear to me how to start.

    1. How do I handle the first version? I have a common version number for all sub projects to indicate that they belong together (lets say 0.9). Therefore the first revision should be 0.9.0, but so far nothing of my projects is in my repository. How do I get Ivy to assign this revision number.

    2. In the course of developing I want to publish the built files again, without changing the revision number so far.

    3. If I'm finished with my work I want to push it to a shared repository (and increase the revision number lets say from 0.9.0 to 0.9.1), what is the recommended approach to do so?

    4. For an actual release, I want to make distributions with dependencies and without, somehow I guess I can use different configurations for that. How can I use that to my advantage?

    • Johnny Hujol
      Johnny Hujol over 11 years
      Just FYI, according to this deliver task is called by the publish task.
  • Peter Lamberg
    Peter Lamberg over 12 years