Java unzip compressed archive with folders FileNotFound exception
Asked Answered
A

2

8

I am trying to unzip an archive in java that contains folders as well as files inside of the archive. The issue is that it throws a FNF exception whenever it gets to the folders and tries to unzip them. My unzip code is as follows:

 private void unZipUpdate(String pathToUpdateZip, String destinationPath){
       byte[] byteBuffer = new byte[1024];

       try{
           ZipInputStream inZip = new ZipInputStream(new FileInputStream(pathToUpdateZip));
           ZipEntry inZipEntry = inZip.getNextEntry();
           while(inZipEntry != null){
               String fileName = inZipEntry.getName();
               File unZippedFile = new File(destinationPath + File.separator + fileName);


               System.out.println("Unzipping: " + unZippedFile.getAbsoluteFile());
               new File(unZippedFile.getParent()).mkdirs();


               FileOutputStream unZippedFileOutputStream = new FileOutputStream(unZippedFile);
               int length;
               while((length = inZip.read(byteBuffer)) > 0){
                   unZippedFileOutputStream.write(byteBuffer,0,length);
               }
               unZippedFileOutputStream.close();
               inZipEntry = inZip.getNextEntry();
           }
           inZipEntry.clone();
           inZip.close();
           System.out.println("Finished Unzipping");
       }catch(IOException e){
           e.printStackTrace();
       }
    }

I thought I had compressed folders handled with

new File(unZippedFile.getParent()).mkdirs();

But that doesn't seem to fix the issue. What am I missing here?

Stacktrace:

Unzipping: D:\UnzipTest\aspell
java.io.FileNotFoundException: D:\UnzipTest\aspell\american-w-accents.alias (The system cannot find the path specified)
    at java.io.FileOutputStream.open(Native Method)
Unzipping: D:\UnzipTest\aspell\american-w-accents.alias
    at java.io.FileOutputStream.<init>(FileOutputStream.java:221)
    at java.io.FileOutputStream.<init>(FileOutputStream.java:171)
    at shopupdater.ShopUpdater.unZipUpdate(ShopUpdater.java:47)
    at shopupdater.ShopUpdater.unZipUpdate(ShopUpdater.java:33)
    at shopupdater.ShopUpdater.main(ShopUpdater.java:67)

"aspell" is a folder that was inside the archive.

I tried Daniel's suggestion of adding

unZippedFile.createNewFile();

after

new File(UnzippedFile.getParent()).mkdirs();

That threw a different exception of:

Unzipping: D:\UnzipTest\aspell
Unzipping: D:\UnzipTest\aspell\american-w-accents.alias
java.io.FileNotFoundException: D:\UnzipTest\aspell\american-w-accents.alias (The system cannot find the path specified)
    at java.io.FileOutputStream.open(Native Method)
    at java.io.FileOutputStream.<init>(FileOutputStream.java:221)
    at java.io.FileOutputStream.<init>(FileOutputStream.java:171)
    at shopupdater.ShopUpdater.unZipUpdate(ShopUpdater.java:56)
    at shopupdater.ShopUpdater.unZipUpdate(ShopUpdater.java:33)
    at shopupdater.ShopUpdater.main(ShopUpdater.java:76)
Amaryl answered 15/10, 2013 at 20:20 Comment(3)
Please post the stacktrace.Cherida
@SotiriosDelimanolis added to original postAmaryl
I'm pretty sure it's because you're not checking if (inZipEntry.isDirectory()), If it's a directory, make it instead of writing bytes.Pyrochemical
G
6

Try this code, it works on my machine (ubuntu)

private static void unZipUpdate(String pathToUpdateZip, String destinationPath){
       byte[] byteBuffer = new byte[1024];

       try{
           ZipInputStream inZip = new ZipInputStream(new FileInputStream(pathToUpdateZip));
           ZipEntry inZipEntry = inZip.getNextEntry();
           while(inZipEntry != null){
               String fileName = inZipEntry.getName();
               File unZippedFile = new File(destinationPath + File.separator + fileName);
               System.out.println("Unzipping: " + unZippedFile.getAbsoluteFile());
               if (inZipEntry.isDirectory()){
                   unZippedFile.mkdirs();
               }else{
                   new File(unZippedFile.getParent()).mkdirs();
                   unZippedFile.createNewFile();
                   FileOutputStream unZippedFileOutputStream = new FileOutputStream(unZippedFile);
                   int length;
                   while((length = inZip.read(byteBuffer)) > 0){
                       unZippedFileOutputStream.write(byteBuffer,0,length);
                   }
                   unZippedFileOutputStream.close();                       
               }
               inZipEntry = inZip.getNextEntry(); 
           }
           //inZipEntry.close();
           inZip.close();
           System.out.println("Finished Unzipping");
       }catch(IOException e){
           e.printStackTrace();
       }
    }
Gobbledygook answered 15/10, 2013 at 20:25 Comment(2)
Where exactly should that be though? Before the initialization of the fileoutputstream?Amaryl
I tried out the updated, it somehow confused files and directories. Hope it works on windows machines the same way.Gobbledygook
M
1

It appears you are processing the directory as a file first and creating an empty file that prevents creation of the directory.

Unzipping: D:\UnzipTest\aspell
Unzipping: D:\UnzipTest\aspell\american-w-accents.alias
java.io.FileNotFoundException: D:\UnzipTest\aspell\american-w-accents.alias

It's hard to be completely sure but that's what it looks like. The first "Unzipping:" line is from when your code created an empty file named D:\UnzipTest\aspell. On the next iteration you tried to create a directory with the same name, and that failed, probably silently, causing the later failure.

Melvin answered 15/10, 2013 at 20:49 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.