Skip to content
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

Extracting ZIP with entry named . deletes the output directory #545

Open
Marcono1234 opened this issue May 20, 2024 · 0 comments
Open

Extracting ZIP with entry named . deletes the output directory #545

Marcono1234 opened this issue May 20, 2024 · 0 comments

Comments

@Marcono1234
Copy link
Contributor

Marcono1234 commented May 20, 2024

Version

Zip4j 2.11.5
Windows 10 (but might apply to Linux as well)

Description

When extracting a ZIP which contains an entry named ., Zip4j deletes the output directory before eventually throwing an exception. This is unexpected and looks like a bug. Zip4j should not delete the output directory, instead the user code should do that, if desired.

The underlying issue seems to be that Zip4j does not ignore an entry named . (respectively throw an exception) but instead treats it as regular file and tries to write to it. However, because it points to the existing output directory, trying to open the directory as file fails. Zip4j then erroneously tries to perform clean-up and actually deletes the directory here:

} catch (Exception e) {
if (outputFile.exists()) {
outputFile.delete();
}

Note: This actually applies to more than just the literal string ., for example also to . (with trailing space). So to detect this is might be best to check the result of getCanonicalPath(), or to adjust AbstractExtractFileTask#unzipFile to fail fast if outputFile is an existing directory (and not try to delete it).

Example code

Path zipPath = Files.createTempFile("zip-test", ".zip");
Path outputDir = Files.createTempDirectory("zip-test");

try (ZipOutputStream zipOut = new ZipOutputStream(Files.newOutputStream(zipPath))) {
    zipOut.putNextEntry(new ZipEntry("."));
}

try (ZipFile zipFile = new ZipFile(zipPath.toFile())) {
    zipFile.extractAll(outputDir.toString());
} catch (ZipException e) {
    System.out.println("Encountered expected exception: " + e);
} finally {
    Files.delete(zipPath);
}
System.out.println("Output dir exists: " + Files.isDirectory(outputDir));

This will unexpectedly print

Output dir exists: false

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant