Why are the dependencies of configuration "A", which is extended by configuration "B", not resolved when those of the configuration "B" are to be?

I have a project that has a source set containing code that is used in both the unit test suite and integration test suite of the project. The code in this source set makes use of functionality defined by the test dependencies shared by the aforementioned test suites.

Here is a snippet of the build.gradle.kts file of the project which attempts to declare dependencies for the aforementioned source set using those already declared for the unit test suite:

dependencies {



val commonTestResourceSourceSet = sourceSets.create("commonTestResource")

val commonTestResourceImplementationConfiguration = configurations.getByName(commonTestResourceSourceSet.implementationConfigurationName)


Attempting to run the unit test suite of the project (using the command ./gradlew test) when the project is configured is such a way results in failure, with error messages like those below which indicate that the dependencies of the configuration that was extended in the snippet were not resolved:

e: /path/to/project/src/commonTestResource/.../foo.kt (3, 8) : Unresolved reference: io
e: /path/to/project/src/commonTestResource/.../foo.kt (11, 44) : Unresolved reference: shouldBe

Declaring the dependencies of interest directly in commonTestResourceImplementationConfiguration, however, enables the commonTestResource source set to be compiled successfully during attempts to run the the unit test suite of the project.

If I understand the documentation, the direct and indirect declaration of dependencies should be functionally equivalent in this scenario:

A configuration can extend other configurations to form an inheritance hierarchy. Child configurations inherit the whole set of dependencies declared for any of its superconfigurations.

Why then, does that not appear to be the case?

You are not extending testImplementation.
You are extending a recursive copy of testImplementation.
Remove the .copyRecursive() and you get the result you expected.

I extended a recursive copy of testImplementation to lazily get around a circular dependency between it and commonTestResourceImplementation. Getting around the problem with a third configuration instead fixed the issue. Thanks!

Though the issue has been resolved, I’m interested in knowing why it arose in the first place. The documentation for copyRecursive() seems to be imply that the configuration it returns should be functionally equivalent to the original in this scenario. For the sake of edification, would you mind explaining why that is not the case?

Honestly, I have no idea.
I just found the copyRecursive() suspicious and for the given example unnecessary.
From the description of it I’d expect the same as you and would say it is worth that you open an issue in GitHub about it.