How do I still publish the artifact with an "archives" or "master" configuration?


(Ryan Nelson) #1

For the new publishing model (“ivy-publish”) starting in Gradle 1.5, it appears the default ivy.xml no longer provides a configuration to obtain the artifact without transitive dependencies. This is the configuration Maven and Ivy call “master” and historically Gradle has published as “archives.”

Take this 1.4 example:

apply plugin: ‘java’

apply plugin: ‘ivy-publish’

group “missing-archives-example”

version “latest”

publishing {

publications {

ivy

}

repositories {

ivy {

url “local-repo”

}

}

}

This produces an ivy.xml with an “archives” configuration that is not transitive:

<?xml version=“1.0” encoding=“UTF-8”?>

<ivy-module version=“2.0” xmlns:m=“http://ant.apache.org/ivy/maven”>

<info organisation=“missing-archives-example”

module=“ivypublishing”

revision=“latest”

status=“integration”

publication=“20130703112232”

/>

<configurations>

<conf name=“archives” visibility=“public” description=“Configuration for archive artifacts.”/>

<conf name=“compile” visibility=“private” description=“Classpath for compiling the main sources.”/>

<conf name=“default” visibility=“public” description=“Configuration for default artifacts.” extends=“runtime”/>

<conf name=“runtime” visibility=“private” description=“Classpath for running the compiled main classes.” extends=“compile”/>

</configurations>

<publications>

<artifact name=“ivypublishing” type=“jar” ext=“jar” conf=“archives,runtime”/>

</publications>

</ivy-module>

Now take a similar 1.5 example, modified slightly to support the new syntax:

apply plugin: ‘java’

apply plugin: ‘ivy-publish’

group “missing-archives-example”

version “latest”

publishing {

publications {

ivy (IvyPublication) {

from components.java

}

}

repositories {

ivy {

url “local-repo”

}

}

}

This produces an ivy.xml with no “archives” or “master” configuration. There are no dependencies in this project, but if there were they would be in the runtime configuration, which would make it impossible to download just the artifact (w/o dependencies).

<?xml version=“1.0” encoding=“UTF-8”?>

<ivy-module version=“2.0”>

<info organisation=“missing-archives-example” module=“ivypublishing” revision=“latest” status=“integration” publication=“20130703112534”/>

<configurations>

<conf name=“default” visibility=“public” extends=“runtime”/>

<conf name=“runtime” visibility=“public”/>

</configurations>

<publications>

<artifact name=“ivypublishing” type=“jar” ext=“jar” conf=“runtime”/>

</publications>

<dependencies/>

</ivy-module>

I could modify the ivy.xml by hand using the descriptor{} approach, but I’d like to know if the Gradle DSL supports this, or if it was removed (by accident or on purpose).

I should note also that publishing WARs (using “from components.web”) does produce an artifact in a “master” configuration.


(Ryan Nelson) #2

I was able to get this to work by modifying the configuration section by hand as seen below. However, I’d still like to know why this was (apparently) removed from Gradle’s functionality in 1.5. If this was intentional, what is the proposed way to get just the artifact with no dependencies?

publishing {

publications {

ivy (IvyPublication) {

from components.java

descriptor {

withXml {

asNode().configurations*.appendNode(“conf”, [name: “archives”, visibility: “public”])

Object o = asNode().publications.artifact.find { it.@type == “jar” }

if(o != null) { o.@conf = “archives, runtime” }

}

}

}

}

repositories {

url “local-repo”

}

}


#3

Hi Ryan As you’re no doubt aware, the new publishing support is a work in progress. One of the goals is to not carry over a lot of baggage from Gradle 1.0, and to focus on adding features on a use-case driven basis.

So in Gradle 1.5 we stripped our ivy/maven descriptor generation to a bare minimum, to avoid locking us into a model that we don’t want to support long term. This was intentional, and for now you’ll need to implement these sorts of ‘old standards’ yourself.

When and how do you use the ‘archives’ configuration? Knowing this will help us to add this feature to the design spec, and add this to the publishing model in the future.


(Ryan Nelson) #4

Hi Daz,

This came up when trying to use legacy Ant+Ivy projects with Gradle. My Gradle build was publishing an artifact in the ‘archives’ configuration that the Ant+Ivy builds were depending on. When that disappeared in 1.5, it took some effort to make it work again. I think the frustrating thing was simply that upgrading Gradle in one build broke the others. (I do realize the plugin is incubating.)

However, you ask a really good question and as I’ve examined my legacy Ant+Ivy builds, I realized they probably shouldn’t be asking for a single JAR in the first place (most of the time when I want a JAR, I also want it’s dependencies). In other words, I should’ve changed those builds rather than Gradle.

I can think of some edge cases where this would have been useful, but they are pretty rare, and it’s always possible to iterate through the runtime dependencies and just filter the original artifact, so there’s already a workaround for them.

Lastly, I realized belatedly that I don’t think Maven actually allows you to do this. The ‘master’ configuration is only an Ivy construct, so perhaps this really isn’t needed in Gradle.


#5

Hi Ryan Thanks for the constructive feedback. I’ve raised GRADLE-2847 to track the issue of providing a configuration that permits interoperability with existing Ant/Ivy builds. This doesn’t mean that we’ll actually implement this, but it allows us to track the requirement.