Why ZipInputStream can't read the output of ZipOutputStream?

后端 未结 5 1928
夕颜
夕颜 2021-01-18 08:20

I\'m stuck with this junit test:

public void test() throws Exception {
    ByteArrayOutputStream out = new ByteArrayOutputStream();
    ZipOutputStream zipOu         


        
相关标签:
5条回答
  • 2021-01-18 08:43

    Same problem here!

    ZipInputStream can't read the output of ZipOutputStream;

    new ZipFile(file) fails with an error

    no possible explanation!

    Archive viewer program opens the zip file just fine!

    SOLUTION: Uh... it wasn't a zip file after all... it was a tar called 'folder.zip'. Archive viewer was smart enough...

    To those with this problem: Double check!!!

    0 讨论(0)
  • 2021-01-18 08:46

    Recently I had a similar problem while reading a zip bytes created using ZipOutputStream.

    The following snippet led to java.lang.NegativeArraySizeException.

    zipEntry = zipInputStream.getNextEntry();
    byte[] bytes = new byte[(int) zipEntry.getSize()];
    

    An quick solution it was to use Apache commons-io IOUtils to read the all bytes of current entry.

    zipEntry = zipInputStream.getNextEntry();
    byte[] bytes = org.apache.commons.io.IOUtils.toByteArray(zipInputStream);
    

    I hope this will be helpful to someone.

    0 讨论(0)
  • 2021-01-18 08:50

    You actually have to read the contents of the entry, then entry.getSize() will return the correct size.

    To read entry use:

        byte[] buf = new byte[1024];
        int len;
        while ((len = zipIn.read(buf)) > 0) {
            // use data;
        }
    
    0 讨论(0)
  • 2021-01-18 08:50

    Read API doc for ZipEntry. It says "if known". You can read the content using the following (it just prints the size of the zipentry, change it process data appropriately):

    ZipEntry entry = zipIn.getNextEntry();
    int BUFSIZE = 1024;
    byte [] buffer = new byte[BUFSIZE];
    int read = 0;
    int total = 0;
    while( (read = zipIn.read(buffer, 0, BUFSIZE)) >0 ) { 
      total += read;
      // what do you want to do with the data read? Do it here
    }   
    System.err.println("Total: " + total);
    
    0 讨论(0)
  • 2021-01-18 08:54

    I found the answer by myself: entry does not contain the correct size, but with each zipIn.getNextEntry() you get a fresh stream to read the content of your entry from. So simply read the stream up to the end and you have the data of your entry.

    In my junit test the last line could look like this:

    byte[] restoredContent = new byte[ 10 ];
    assertEquals( 3, zipIn.read( restoredContent ) );
    

    Now everything works fine.

    0 讨论(0)
提交回复
热议问题