Создать Java-Zip-архив из существующего OutputStream

Можно ли создать Zip-архив на Java, если я не хочу записывать полученный архив на диск, а отправить куда-то еще?

Идея состоит в том, что создавать файл на диске может быть пустой тратой времени, когда вы хотите отправить Zip-архив пользователю через HTTP (например, из базы данных-BLOB или любого другого хранилища данных).

Я хотел бы создать

java.util.zip.ZipOutputStream 

or a

apache.commons.ZipArchiveOutputStream

где Feeder будет ByteArrayOutputStream из моего репозитория Subversion


person trajectory    schedule 25.10.2010    source источник


Ответы (4)


Да это абсолютно возможно!

Создайте запись Zip, используя метод putNextEntry для ZipOutputStream, затем поместите байты в файл в zip, вызвав write для ZipOutputStream. Для параметра для этого метода, byte[], просто извлеките их из ByteArrayOutputStream с помощью его метода toByteArray.

И ZipOutputStream можно отправить куда угодно, так как его конструктор просто принимает OutputStream, так что может быть, например. ваш HTTP-ответ.

person Adrian Smith    schedule 25.10.2010
comment
Хорошо, это сработало! Но как мне создать каталоги, которые на самом деле содержат сами файлы? Прямо сейчас я получаю все файлы, все в порядке, но каталоги распаковываются как файлы с нулевой длиной в корневом узле, поэтому никакой иерархии нет :-( - person trajectory; 26.10.2010
comment
ZIP-файлы просто содержат плоский список файлов. Однако имена файлов могут содержать информацию о пути. Просто добавьте ZipEntry с таким именем, как dir/file.txt: то есть file.txt в каталоге dir. - person Adrian Smith; 26.10.2010
comment
Да, добавив абсолютный URL-адрес, все работает ожидаемо. Большое спасибо! - person trajectory; 26.10.2010

Что-то вроде этого будет работать:

ZipOutputStream zs = new ZipOutputStream(outputStream) ;
ZipEntry e = new ZipEntry(fileName);
zs.putNextEntry(e);
zs.write(...);
zs.close();
person Eugene Kuleshov    schedule 25.10.2010

Ввод: D:/in.xml

Вывод: D:/final.zip (имеет 2 файла 001zip.txt, 002zip.txt)

Код:

package com.stackoverflow.filezip;

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.zip.ZipEntry;
import java.util.zip.ZipOutputStream;

public class fileZip {

public static void main(String[] args) {

    try {
InputStream in = new FileInputStream("D:/in.xml");
OutputStream out=   new FileOutputStream("D:/final.zip");
ZipOutputStream zs = new ZipOutputStream(out);

            ZipEntry e1 = new ZipEntry("001zip.txt");
            ZipEntry e2 = new ZipEntry("002zip.txt");
            zs.putNextEntry(e1);
            zs.write("test content in file1".getBytes());
            zs.putNextEntry(e2);
            zs.write("test content in file2".getBytes());

            zs.close();
       }
       catch (Exception e) {
            e.printStackTrace();
                           }
                                       }
                       }
person kingAm    schedule 08.05.2015

Используйте Apache Commons Compress:

<dependency>
    <groupId>org.apache.commons</groupId>
    <artifactId>commons-compress</artifactId>
    <version>1.16.1</version>
 </dependency>

Прочитать zip из byte[] bytes примера:

try (ZipArchiveInputStream zis = new ZipArchiveInputStream(
         new ByteArrayInputStream(bytes), "UTF8", false, true)) {
    ZipArchiveEntry ze;
    while ((ze = zis.getNextZipEntry()) != null) {
        log.info(ze.getName());
    }
}
person kinjelom    schedule 27.03.2018