Clean task removes temporary directory

Hey folks,
when we try to run the following command in gradle: ‘gradle subproject:clean subproject:test’ our tests crash. The reason being, that the temporary directory provided by the test task (and which is used by the test classes) does not exist.

Diving into gradle code we figured out, that the temporary directory is created during configuration phase. Which explains why the execution of the clean task deletes the folder again.

Is this expected behaviour? We are asking because it is kind of counterintuitive compared to the way gradle normaly behaves (describe how to do things in configurations phase and execute them in execution phase).

Can you think of an elegant fix to our problem? (A task that recreates the directory is not elegant.)
Or are we missing something? Maybe it is convention that the temporary directory of a task should only be used for the task itself?

Thank you for any clarification on that topic.

1 Like

Things to consider

  1. You could initialize a temp directory in a doFirst() block
def tempDir = file("$buildDir/temp")
test.doFirst {
   delete tempDir
   tempDir.mkdirs()
   file("$tempDir/test.txt") << "Hello world"
}
sourceSets {
   test {
      resources {
         // add tempDir to test runtime classpath 
         srcDir tempDir
      } 
   } 
} 
  1. Use junit’s TemporaryFolder

Thank you for your answer.

We decided against the first solution because we don’t wanted to do this handling by our own when gradle provides this functionality to us.
For your second point we use it already and exactly there the error is thrown because we set the gradle provided temporary folder as root for junit’s TemporaryFolder.

When you refer to the ‘temporary directory’ are you referring to “$buildDir” (ie projectDir/build)?

More than one gradle task creates files / folders under $buildDir and it’s likely that tasks create $buildDir on-demand (eg when creating “$buildDir/classes”).

Regardless of when $buildDir is created, it should exist by the time your tests are running

  1. Can you include a relevant code snippet(s) which uses the temp directory?
  2. Is there at least one class being compiled by the project?

If it were me, I’d use a subdirectory under $buildDir and would create $buildDir if it doesn’t already exist as with my first example

No I refer to $buildDir/tmp/<task name> folder. Thats the folder we get with a tasks property temporaryDir.

We get the value during configuration which creates the folder and afterwards the clean task executed and deletes it. Then the test task itself runs and can’t access it anymore.

To 1:
We configure it
test {
systemProperties = System.getProperties()
systemProperty ‘java.io.tmpdir’, temporaryDir
}

And then use Junit’s TemporaryFolder class.

To 2: Yes

From the code that I saw in AbstractTask in the gradle repository it looks like the folder is created during getting the value and this seems to lead to the problem if you call “gradle clean test”.

Ah, sorry… I wasn’t aware of this directory. It looks like a bug as the javadoc states that “the directory will already exist”