Refer to a Dependency as part of a DSL

I am working on a plugin that needs to be told one or more dependencies upon which to perform a transformation. But I am really not sure how to reference a Dependency specifically. How does one usually do that? E.g., in the example below how would I reference the Dependency for ‘org.hibernate:hibernate-core’ in dependencyToTransform?

dependencies {
    api 'org.hibernate:hibernate-core'
}
...
transformations {
    transformation( "orm" ) {
        dependencyToTransform ???
    }
}

A bit heavy-handed, but I know I could use dedicated Configurations per dependency I want to transform and then pass along the project.configurations.X references. E.g.

dependencies {
    orm 'org.hibernate:hibernate-core'
}
...
transformations {
    transformation( "orm" ) {
        configToTransform project.configurations.orm
    }
}

Any ideas?

NOTE : the “orm” name used for the transformation is just a domain-container-name.

Can you clarify if you just need a Dependency for the transform or if you’re specifically wanting a Dependency that is already part of another configuration, just not a separate one for each transform?

i.e. would your plugin work if you could do this (and you can get a Dependency for it behind the scenes)?

transformations {
    transformation('orm') {
        dependencyToTransform 'org.hibernate:hibernate-core'
    }
}

Hello again James!

Your updated comment its pretty similar to what I have actually (great minds!).

I should have waited to ask this. I am still in the middle of prototyping this and it is fairly complex. I’ll let it percolate for a bit and get back.


As background, this comes from stuff I am prototyping related to the JakartaTransformer tool. You can read some of the back-ground if you wish @ Additional JAR file - variant versus classifier - #2 by Steve_Ebersole

The structure we came up with so far (happy to hear better ways) is to create a “shadow” of the projects from our build that we want to transform. E.g., we need to transform hibernate-core, so we have a separate project named hibernate-core-jakarta which defines a dependency on hibernate-core. hibernate-core-jakarta has absolutely no sources of its own. It’s whole purpose is to be the place where this transformation happens and at the end of the day to present the transformations as its own artifacts. In between is pretty wide open. We have a mostly working solution, I’m just trying to Gradle-fy it.

The tricky part is handling transitive dependencies. E.g. Hibernate exposes some things from JTA. Like all other EE specs, that one now has a Jakarta EE parallel. So when we transform our JAR, we also need to be able to adjust those GAVs as well. At the moment, we basically have to manually rewrite the hibernate-core dependencies block in hibernate-core-jakarta to work around this. Though I highly suspect I will be able to handle those transitively during resolution to dynamically swap GAV for select dependencies

What I ended up with was this:

transformations {
    ...

    shadow( 'org.hibernate:hibernate-core:...' ) {
        ...
    }
}

Where the passed value is any format understood by Gradle. Worked like a champ.

If I can add a related, follow up question… Like mentioned, the point of this “shadow” part is to allow taking one dependency, apply the JakartaTransformer tool and present the transformed JARs as the artifacts for the project applying this transformation.

I am curious… is there any benefit (and then possible) to expose both apiElements / runtimeElements variants? If so, the thing I cannot figure out is how to access all of the variants for a module dependency.

Relatedly… if the dependency defines multiple artifacts (sources, javadoc, etc) is there any way to access those relative to the default dependency? Or would I have to create new Dependency refs behind the scene to get those?