-
Notifications
You must be signed in to change notification settings - Fork 5
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Fix] JDK is successfully installed if bin/java
files exist
#452
Conversation
Generate changelog in
|
bin/java
existsbin/java
or sentinel
files exist
…adle-jdks into cr/more-sanity-checks-script
bin/java
or sentinel
files existbin/java
files exist
echo "Successfully installed JDK distribution in $jdk_installation_directory" | ||
elif [ ! -f "$jdk_installation_directory/bin/java" ]; then | ||
echo "Java executable not found in $jdk_installation_directory/bin/java, re-installing the JDK...." | ||
else | ||
echo "JDK installation $jdk_installation_directory was already configured" | ||
continue | ||
fi |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
the github diff is weird, the only changes I have made is adding the if-else conditions to check if the directory and/or bin/java files exists at the top. the rest of the code is unchanged
@@ -153,7 +159,8 @@ private static void writeFileContent(Path path, String content) throws IOExcepti | |||
Files.writeString(path, content + "\n"); | |||
} | |||
|
|||
private void dockerBuildAndRunTestingScript(String baseImage, String shell, boolean installCurl) | |||
private void dockerBuildAndRunTestingScript( | |||
String baseImage, String shell, boolean installCurl, boolean addEmptyGradleJdkDir) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I assumed this meant the ~/.gradle/gradle-jdks
dir - maybe call this just addJdkDir
?
logger.log("Cannot move the directory to the final directory, attempting to do a non-atomic operation"); | ||
Files.move(tempDirWithPrefix, destinationJdkInstallationDirectory, StandardCopyOption.REPLACE_EXISTING); | ||
} | ||
createSentinelFile(destinationJdkInstallationDirectory); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What is this sentinel file used for?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think it's used elsewhere in this diff and now we have the atomic move the directory/java binary existing should be enough.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am thinking that the sentinel file is the flag that tells us if the installation finished successfully. I was thinking that in the future (if we add the check now , we would re-install jdks that are already correctly installed on user's laptops) we might assume that the installation was successful if the file was created.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would hope that since we move the JDK now it will definitely be fine as the move will mean the directory is either there and correct or not there, rather than just partially copied.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ack, I'll remove this then
logger.log(String.format("Distribution URL %s already exists", destinationJdkInstallationDirectory)); | ||
return false; | ||
} | ||
logger.log( | ||
String.format("Copying JDK from %s into %s", currentJavaHome, destinationJdkInstallationDirectory)); | ||
FileUtils.copyDirectory(currentJavaHome, destinationJdkInstallationDirectory); | ||
Path tempDirWithPrefix = Files.createTempDirectory("gradle-jdks"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Atomic moves generally only work when the source and destination for the filesystem object are on the same filesystem. If they're not it's usually actually a copy. I think here this risks copying to a tmp filesystem, then copying again to the filesystem ~/.gradle/gradle-jdks
is mounted on rather than moving to the final destination.
To work around this, I'd make a tmp
dir at ~/.gradle/gradle-jdks/tmp
and copy it to a subdir in there first before moving. It should definitely be on the same filesystem then.
logger.log(String.format("Distribution URL %s already exists", destinationJdkInstallationDirectory)); | ||
return false; | ||
} | ||
logger.log( | ||
String.format("Copying JDK from %s into %s", currentJavaHome, destinationJdkInstallationDirectory)); | ||
FileUtils.copyDirectory(currentJavaHome, destinationJdkInstallationDirectory); | ||
Path tempDirWithPrefix = Files.createTempDirectory("gradle-jdks"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would also delete the temp dir if it still exists in a try-finally to make sure it's cleaned even if there's an exception. Don't want an ever increasing number of these.
@@ -65,13 +66,13 @@ public FileVisitResult preVisitDirectory(Path dir, BasicFileAttributes _attrs) t | |||
|
|||
@Override | |||
public FileVisitResult visitFile(Path file, BasicFileAttributes _attrs) throws IOException { | |||
Files.copy(file, destination.resolve(source.relativize(file))); | |||
Files.copy(file, destination.resolve(source.relativize(file)), StandardCopyOption.REPLACE_EXISTING); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we still need to replace-existing with the copy to a temp location and then move?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it is still better to keep the replace-existing, otherwise if some crash leaves the tmp location un-deleted, then we can recover from it.
"$java_home"/bin/java -cp "$scripts_dir"/gradle-jdks-setup.jar com.palantir.gradle.jdks.setup.GradleJdkInstallationSetup jdkSetup "$jdk_installation_directory" || die "Failed to set up JDK $jdk_installation_directory" | ||
echo "Successfully installed JDK distribution in $jdk_installation_directory" | ||
elif [ ! -f "$jdk_installation_directory/bin/java" ]; then | ||
echo "Java executable not found in $jdk_installation_directory/bin/java, re-installing the JDK...." |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think worth having a comment about the possibly broken existing JDKs.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this file will be added to all the repos (it is used both by the docker images and the gradle jdk enabled repos). Is it OK to mention the possibly broken JDKs in a comment ?
tempCopyDir, | ||
destinationJdkInstallationDirectory, | ||
StandardCopyOption.REPLACE_EXISTING, | ||
StandardCopyOption.ATOMIC_MOVE); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The common filesystems (ieg APFS/NTFS/ext4) all support atomic moves... but perhaps we should handle the AtomicMoveNotSupportedException
like before just incase this ends up on a different filesystem that doesn't?
Released 0.54.0 |
Before this PR
Context: https://pl.ntr/2p9
We consider that a JDK was successfully installed if the directory exists.
However, this is not always true. eg. if an exception happens while the JDK is copied over to the destination directory (https://github.com/palantir/gradle-jdks/blob/develop/gradle-jdks-setup/src/main/java/com/palantir/gradle/jdks/setup/GradleJdkInstallationSetup.java#L130). The JDK directory might not contain the
bin/java
executable.After this PR
A JDK directory is considered successfully installed if
bin/java
exists .I am also doing a copy to a temporary directory and an atomic move to the destination directory.
A
sentinel
file is added at the end of a successful installation - I think we might want to use this in the future to check if the jdk was successfully installed or not.Note: I am not considering for now only the
sentinel
file to be the source of truth because of backwards compatibility (the jdks we installed so far won't have thesentinel
file).==COMMIT_MSG==
[Fix] JDK is successfully installed if
bin/java
exists==COMMIT_MSG==
Possible downsides?