The goal: iterate over Configuration
instances, dumping information about resolved artifact IDs. Note this needs to be artifacts not components because I want to distinguish myproject-1.2.3.jar
from myproject-1.2.3-someclassifier.jar
, and only the artifact layer knows about this.
Where a Configuration
depends on another subproject, I do not want to have to cause an actual build of other-subproject-artifact.jar
; either seeing its ID but not having the JAR available, or just skipping it entirely is fine (I am only interested in external dependencies). Downloading actual external JARs is acceptable, but not necessary; I only want to know what JAR would be required.
In Gradle < 8 without the configuration cache in play, configuration.resolvedConfiguration.lenientConfiguration.artifacts
is exactly what I want. Surprisingly, it directly exposes classifier
, even though that’s a bit Maven-specific. Useful though.
With the configuration cache, we’re not supposed to just go digging through Project
at task execution time. Fair enough. The suggested resolution for dealing with artifacts is to consume configuration.incoming.artifacts.resolvedArtifacts
, a Provider<Set<ResolvedArtifactResult>>
, as the task input. Sounds good, but when there are intra-project dependencies I can’t access it without causing a full build, since other-subproject-artifact.jar
doesn’t exist yet and even though I only want the ID, the API would expose a File
and that doesn’t exist yet.
Alright, let’s try artifactView { it.lenient(true) }
(or similarly, filtering out the offending intra-project artifacts with a selector) instead – unfortunately this doesn’t work either, because the pre-check on trying to access the resolved artifacts isn’t lenient in the way I might hope, also raising the objection that some artifacts would be produced by tasks that haven’t run yet. Again, it looks as if a full build would be necessary.
Lifting the lid on DefaultConfiguration
and DefaultConfigurationResolver
I can see that DefaultResolverResults.visitedArtifacts
has exactly what I want – information about the artifacts that will be needed, though they may not exist yet because a build or download is pending, plus visitors to walk over them – but these are unstable internal interfaces. The lenientConfiguration
of course gets populated with what I’d want too, but I don’t see a way to access this that is configuration-cache friendly.
At this point I gave up, called notCompatibleWithConfigurationCache
and did things the old way. But it would be better not to have to do that, and it seems likely this escape hatch may go away in the future.
So, how can I get this information out in a config-cache-friendly manner?