gradle-docker-plugin icon indicating copy to clipboard operation
gradle-docker-plugin copied to clipboard

Configuration cache support

Open Sineaggi opened this issue 2 years ago • 2 comments

When trying to use the gradle configuration cache, depending on the plugins applied and tasks configured various configuration cache problems will prevent builds from succeeding.

There are a few main issues that are in this project, listed below. Most of these were captured by taking the existing functional tests and adding --configuration-cache to the build arguments.

A set of issues related to calling project at task action time

- Task `:buildImage` of type `com.bmuschko.gradle.docker.tasks.image.DockerBuildImage`: invocation of 'Task.project' at execution time is unsupported.
  See https://docs.gradle.org/7.4.2/userguide/configuration_cache.html#config_cache:requirements:use_project_during_execution

Most of these can be resolved by importing the relevant factory and using that instead. So in the case of the Dockerfile task, we can add a new private final ObjectFactory objects and replace getDestDir's call to project.objects.directoryProperty() with objects.directoryProperty()

One is related to the build listener api (for the docker client)

- Unknown location: registration of listener on 'Gradle.buildFinished' is unsupported
  See https://docs.gradle.org/7.4.2/userguide/configuration_cache.html#config_cache:requirements:build_listeners

This one requires a bit of rework. Gradle has been pushing developers a bit more towards build services for cases where a task potentially wants to share state.

One is related to internal variables (i.e. task outputs)

From what I can tell, this mostly comes around due to the way tests are written, and can be confusing to track down. I was able to fix these by making (for example) the @Internal Property<String> imageId base mapped from it's imageIdFile output property. Something like imageId.set(imageIdFile.map { it.asFile.text }

One is a strange reoccurring bug, potentially related to groovy closures.

Execution failed for task ':buildImage'.
> Cannot cast object 'java.lang.Object@56ee54b7' with class 'java.lang.Object' to class 'org.gradle.api.DefaultTask'

The places I've seen this issue show up the most is when upToDateWhen captures the original task, and not properties/providers. I'm not sure if this is a groovy or gradle bug, but the easiest fix was to create a local variable, then reference that in the closure.

// for example, this line fixes the above exception.
def imageIdFile = this.imageIdFile
outputs.upToDateWhen {
    // here's where the capture gets queried
    File file = imageIdFile.get().asFile

EDIT: Another workaround seems to be manually implementing the Spec<Task> interface.

Sineaggi avatar Oct 03 '22 02:10 Sineaggi

For example, a specific issue in the Dockerfile task is the destDir property.

7 problems were found storing the configuration cache, 2 of which seem unique.
- Task `:dockerCreateDockerfile` of type `com.bmuschko.gradle.docker.tasks.image.Dockerfile`: invocation of 'Task.project' at execution time is unsupported.
  See https://docs.gradle.org/7.4.2/userguide/configuration_cache.html#config_cache:requirements:use_project_during_execution
- Task `:dockerCreateDockerfile` of type `com.bmuschko.gradle.docker.tasks.image.Dockerfile`: value 'provider(?)' failed to unpack provider

The fix in this case is to use the ObjectFactory as per https://github.com/bmuschko/gradle-docker-plugin/compare/master...Sineaggi:gradle-docker-plugin:remove-project-call-at-runtime

Which then lowers our configuration cache issues

1 problem was found storing the configuration cache.
- Task `:dockerCreateDockerfile` of type `com.bmuschko.gradle.docker.tasks.image.Dockerfile`: value 'provider(?)' failed to unpack provider

Sineaggi avatar Oct 03 '22 02:10 Sineaggi

Although https://github.com/bmuschko/gradle-docker-plugin/pull/1103 fixes the above issue, it doesn't fix all of the configuration issues in the DockerJavaApplicationPluginFunctionalTest. I've opted to add a new test that only tests the docker file creation task for now.

Sineaggi avatar Oct 03 '22 03:10 Sineaggi

Were you planning to provide more PRs on this before the next major release?

bmuschko avatar Oct 20 '22 15:10 bmuschko

Here's the next big one, related to the DockerBuildImage task as well as the more general AbstractDockerRemoteApiTask. https://github.com/bmuschko/gradle-docker-plugin/pull/1108

I've rebased it and tried to provide context for each of the changes in the pr.

Sineaggi avatar Oct 20 '22 20:10 Sineaggi

I haven't checked yet but does your PR fully support the configuration cache for this plugin?

bmuschko avatar Oct 31 '22 16:10 bmuschko

Not fully, now that the build service was added to AbstractDockerRemoteApiTask migrating the other tasks is unblocked.

Sineaggi avatar Oct 31 '22 16:10 Sineaggi

This ticket should be mostly complete now. We can close this and open a new 'configuration cache leftovers', or just tackle issues as they're reported going forwards.

Sineaggi avatar Nov 06 '22 22:11 Sineaggi

Great, thanks. We'll release a new version with your changes and then fix forward.

bmuschko avatar Nov 09 '22 01:11 bmuschko

Thanks again for your great work on this!

bmuschko avatar Nov 12 '22 13:11 bmuschko