Jendrik Johannes
12/12/2024, 11:17 AM@Incremental
tasks do:
• When the task first runs, I store a hash of the output somewhere
◦ Here I may also do some filtering if required for selected tools to cater for (3)
• Before I actually extract the Zip, I hash the existing output folder and check if the hash has changed. Only when it changed I clear the output and re-extract.
My question:
• I am hoping to reuse an existing Gradle Service for the solution I sketched – even though it is internal API. I am looking at ChecksumService
, but that's for single files. Is there something I can use out-of-the-box to process the whole destination directory? @wolfs maybe you have a pointer for me?
• Any alternative ideas?wolfs
12/12/2024, 11:30 AMInputChanges
and the changes are non-incremental. Changing the task classpath is non-incremental…
For a regular task, that won’t happen right now, so you might make it work.
For actually obtaining the output hashes, I wonder if you would be able [the OutputFileChanges
from up-to-date checks](https://github.com/gradle/gradle/blob/e3a8405909d78e6e586893e4fdcaece11c855968/pla[…]cution/history/changes/DefaultExecutionStateChangeDetector.java). Gradle has the information already, so it would be better to re-use. It might currently be impossible from a task action, though. For reading snapshots from disk, FileSystemAccess
would be the right service, though again, it is internal and might change. If you use it to read the outputs during the task action, you might need to call FileSystemAccess.invalidate()
to make sure Gradle doesn’t re-use possibly changed output.ephemient
12/12/2024, 11:51 AMAdam
12/12/2024, 1:53 PMJendrik Johannes
12/12/2024, 4:51 PMInputChanges
(but a plain one). Just mentioned it for comparison. I will experiment if I can get to the task outputs as you described.
@Adam that's very interesting. Do you know some more details? If the extracted folder is treated as an ivy repo, each file needs to be presented as a separate downloadable artifact right? You can't download a folder. Does the approach create some artificial metadata that lists all the individual files that were extracted as artifacts?Adam
12/12/2024, 5:54 PMDo you know some more details? If the extracted folder is treated as an ivy repo, each file needs to be presented as a separate downloadable artifact right? You can't download a folder.Yeah that's right, I think it creates an IvyModule for each requested file, on demand https://github.com/JetBrains/intellij-platform-gradle-plugin/blob/6af3294df1691ee1a1d817fecac1bb6a22f4b37a/src/main/kotlin/org/jetbrains/intellij/platform/gradle/shim/PluginArtifactoryShim.kt#L65-L74
Jendrik Johannes
12/13/2024, 7:25 AMFileSystemAccess
is exactly what I was looking for. We will try this approach first. Thanks again for the pointers @wolfs!Jendrik Johannes
12/13/2024, 11:09 AMJendrik Johannes
01/29/2025, 7:43 AMDependencyManagementServices
and FileSystemAccess
. I created this issue to discuss if these could become available as public API in some form. I think this would be really useful for a couple of use cases:
• https://github.com/gradle/gradle/issues/32225Adam
02/22/2025, 9:05 AMoutputs.upToDateWhen { hashFile.readText() != currentChecksum }
check to my ToolInstallerTask, otherwise the content could change on disk and Gradle wouldn't realise and re-run the task. Maybe there's a better way?
I think the internal util for generating a checksum could be re-implemented with public types (use a FileCollection to access all files and their relative paths, and Java's MessageDigest to create a checksum). I'll attach a demo below. However, the Gradle checksum utils have some reference to Gradle's VFS - is there some benefit to using the VFS?Adam
02/22/2025, 9:06 AMJendrik Johannes
02/24/2025, 6:56 AMMaybe your use case is different than mine, but I explicitly do NOT want the task to rerun on changes to the tool installation. The tool is an implementation detail in the task action. I do not care what state it is in to decide if the task runs or not. Only if the task needs to run, and the tool is not present (or has an invalid installation) I want to download/extract i.outputs.upToDateWhen { ...
...util for generating a checksum could be re-implemented with public typesThanks for sharing. The reason I used the Gradle service: 1. I just don't want to think about it and don't want to maintain any own code in this area 2. I believe the Gradle implementation does caching. So you can repeatedly call
read()
for the same folder and the checksum won't be re-computed (that's why there is also an invalidate()
). Concretely, one colleague in the project was concerned that with the solution, if like 100 tasks use the same tool within one build run, they would all re-compute the checksum. And since some tools are more than 1gb large this may be expensive (I don't know how expensive it really is though).Adam
02/24/2025, 9:44 AMI explicitly do NOT want the task to rerun on changes to the tool installationWhat about if the tool installation dir is deleted? Without checking the install dir, Gradle is only aware of the checksum file. If the checksum file doesn't change, will the deleted tool be re-installed?
Jendrik Johannes
02/25/2025, 2:06 PMAdam
02/25/2025, 2:14 PMJendrik Johannes
02/25/2025, 2:15 PM