[updater] fixing directory symlink removal

GitOrigin-RevId: 05b3333b66f2f127e61e9af91594b4aad6124d20
This commit is contained in:
Roman Shevchenko
2020-02-25 21:10:27 +00:00
committed by intellij-monorepo-bot
parent 7526651cf8
commit 31d2dc133c
3 changed files with 22 additions and 8 deletions
@@ -5,7 +5,6 @@ import java.io.*;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.LinkOption;
import java.nio.file.attribute.BasicFileAttributes;
import java.util.zip.ZipEntry;
import java.util.zip.ZipFile;
import java.util.zip.ZipOutputStream;
@@ -23,8 +22,7 @@ public class CreateAction extends PatchAction {
protected void doBuildPatchFile(File olderFile, File newerFile, ZipOutputStream patchOutput) throws IOException {
patchOutput.putNextEntry(new ZipEntry(getPath()));
BasicFileAttributes attrs = Files.readAttributes(newerFile.toPath(), BasicFileAttributes.class, LinkOption.NOFOLLOW_LINKS);
if (!attrs.isDirectory()) {
if (!Files.isDirectory(newerFile.toPath(), LinkOption.NOFOLLOW_LINKS)) {
FileType type = getFileType(newerFile);
writeFileType(patchOutput, type);
if (type == FileType.SYMLINK) {
@@ -1,9 +1,13 @@
// Copyright 2000-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
// Copyright 2000-2020 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file.
package com.intellij.updater;
import java.io.DataInputStream;
import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.LinkOption;
import java.nio.file.Path;
import java.util.stream.Stream;
import java.util.zip.ZipFile;
import java.util.zip.ZipOutputStream;
@@ -53,17 +57,27 @@ public class DeleteAction extends PatchAction {
@Override
protected void doApply(ZipFile patchFile, File backupDir, File toFile) throws IOException {
Runner.logger().info("Delete action. File: " + toFile.getAbsolutePath());
//NOTE: a folder can be deleted only in case if it does not contain any user's files/folders.
String[] children;
if (!toFile.isDirectory() || (children = toFile.list()) != null && children.length == 0) {
// a directory can be deleted only when it does not contain any user's content
boolean canDelete = true;
if (Files.isDirectory(toFile.toPath(), LinkOption.NOFOLLOW_LINKS)) {
try (Stream<Path> children = Files.list(toFile.toPath())) {
canDelete = !children.findAny().isPresent();
}
}
if (canDelete) {
Runner.logger().info("Delete: " + toFile.getAbsolutePath());
Utils.delete(toFile);
}
else {
Runner.logger().info("Preserved: " + toFile.getAbsolutePath());
}
}
@Override
protected void doRevert(File toFile, File backupFile) throws IOException {
if (!toFile.exists() || toFile.isDirectory() || isModified(toFile)) {
if (!toFile.exists() || Files.isDirectory(toFile.toPath(), LinkOption.NOFOLLOW_LINKS) || isModified(toFile)) {
Utils.delete(toFile); // make sure there is no directory remained on this path (may remain from previous 'create' actions
Utils.copy(backupFile, toFile);
}
@@ -606,6 +606,8 @@ public abstract class PatchApplyingRevertingTest extends PatchTestCase {
Files.createSymbolicLink(myOlderDir.toPath().resolve("A.framework/Versions/Current"), Paths.get("A"));
Files.createSymbolicLink(myOlderDir.toPath().resolve("A.framework/Libraries"), Paths.get("Versions/Current/Libraries"));
Files.createSymbolicLink(myOlderDir.toPath().resolve("A.framework/Resources"), Paths.get("Versions/Current/Resources"));
Files.createDirectories(myOlderDir.toPath().resolve("Home/Frameworks"));
Files.createSymbolicLink(myOlderDir.toPath().resolve("Home/Frameworks/A.framework"), Paths.get("../../A.framework"));
randomFile(myNewerDir.toPath().resolve("A.framework/Versions/A/Libraries/lib1.dylib"));
randomFile(myNewerDir.toPath().resolve("A.framework/Versions/A/Libraries/lib2.dylib"));