TestKit: easiest correct way of getting the code under test into the test build

I develop a Gradle plugin and in my project I inject the code under test into the test build in a manner that differs from one mentioned in https://docs.gradle.org/2.9/userguide/test_kit.html#N14FD7

I use a system property and a doFirst() block instead of a classpath file and a separate task. Also I exclude dependencies on a local Gradle API and Groovy to prevent interference with a Gradle version passed to a GradleRunner.

For me my approach looks more clean and simple than one from the user guide (no interaction with filesystem, no redundant dependencies on classpath, no new tasks), so I wonder why the user guide’s method is so complicated? Maybe I’ve overlooked something and my code has some flaws?

Here is my test configuration from build.gradle:

{
  doFirst
    {
      def classpathFiles = project.sourceSets.main.output.files + configurations.runtime.files -
          configurations.detachedConfiguration(dependencies.gradleApi(), dependencies.localGroovy())
      systemProperties = ['test.classpath.files': classpathFiles.collect{it.canonicalPath}.join(';')]
	}
}```

There’s three problems:

  1. This assumes that the classes under test are also inputs to the test task (which they do happen to be in this case), and therefore any change in them will invalidate the up-to-date ness of the task
  2. Use a system property for this is problematic on Windows with its cripplingly small maximum command length
  3. You’ll have issues with meta characters in filenames on Windows

So in summary, if you are using a simple conventional project structure (e.g. out of the box Test task setup) and aren’t using Windows then this will work fine.

The pattern that we encourage in the user guide is more easily transferrable to non conventional setups and is “safe” on Windows.