简体   繁体   中英

Java - Adding File to the Archive without deleting other files

So I have this code, it pretty much does what it should but my archive ends up broken and it doesn't save the files. Of course I have to achieve these without using FileSystem, no TempFiles or anything.

    public static void main(String[] args) throws IOException {
    //        Path fileName = Paths.get(args[0]);
    //        String pathZip = args[1];
            Path fileName = Paths.get("C:\\Users\\dell\\Desktop\\addfile.txt");
            String pathZip = "C:\\Users\\dell\\Desktop\\test.zip";
            Map<String, byte[]> zipEntryMap = addFilesInMap(pathZip);
            zipEntryMap.forEach((zipEntryName, bytes) -> {
                System.out.println(zipEntryName+" "+bytes.toString());
                try {
                    containAndSaveSameFiles(pathZip, bytes, zipEntryName);
                } catch (Exception e) {
                    e.printStackTrace();
                }
            });
    //        saveFileInArchive(fileName, pathZip);
        }
        private static Map<String, byte[]> addFilesInMap(String pathZip) throws IOException {
            Map<String, byte[]> zipEntryMap = new HashMap<>();
            FileInputStream fileInputStream = new FileInputStream(pathZip);
            ZipInputStream zipInputStream = new ZipInputStream(fileInputStream);
            ZipEntry zipEntry;
            while((zipEntry = zipInputStream.getNextEntry())!= null){
                byte[] buffer = new byte[1024];
                ByteArrayOutputStream builder = new ByteArrayOutputStream();
                int end;
                while((end = zipInputStream.read(buffer)) > 0){
                    builder.write(buffer, 0, end);
                }
                zipEntryMap.put(zipEntry.getName(), builder.toByteArray());
            }
            return zipEntryMap;
        }
        private static void containAndSaveSameFiles(String pathZip, byte[] bytes, String zipEntryName) throws Exception{
            ByteArrayOutputStream readBytes = new ByteArrayOutputStream();
            FileOutputStream fileOutputStream =  new FileOutputStream(pathZip);
            ZipOutputStream outputStream = new ZipOutputStream(readBytes);
            ZipEntry zipEntry2 = new ZipEntry(zipEntryName);
            zipEntry2.setSize(bytes.length);
            outputStream.putNextEntry(new ZipEntry(zipEntryName));
            outputStream.write(bytes);
        }
        private static void saveFileInArchive(Path fileToBeAdded, String pathToArchive) throws IOException {
            FileOutputStream fileOutputStream = new FileOutputStream(pathToArchive);
            ZipOutputStream zipOutputStream = new ZipOutputStream(fileOutputStream);
            zipOutputStream.putNextEntry(new ZipEntry("new/"+fileToBeAdded.getFileName()));
            Files.copy(fileToBeAdded, zipOutputStream);
            zipOutputStream.close();
            fileOutputStream.close();
        }

I tried a few ways, and look up on the internet but can't find any good answer. Thank you for help.

Your code is almost correct.

Bug No:1 in containAndSaveSameFiles Using readBytes instead of fileOutputStream .

Bug No:2 in saveFileInArchive Rewriting OutputStream by reopening it again.

Complete code after review:

    public static void main(String[] args) throws IOException {
        //        Path fileName = Paths.get(args[0]);
        //        String pathZip = args[1];
        Path fileName = Paths.get("C:\\Users\\dell\\Desktop\\addfile.txt");
            String pathZip = "C:\\Users\\dell\\Desktop\\test.zip";
        Map<String, byte[]> zipEntryMap = addFilesInMap(pathZip);
        FileOutputStream fileOutputStream =  new FileOutputStream(pathZip);
        ZipOutputStream zipOutputStream = new ZipOutputStream(fileOutputStream);
        zipEntryMap.forEach((zipEntryName, bytes) -> {
            System.out.println(zipEntryName+" "+bytes.toString());
            try {
                containAndSaveSameFiles(pathZip, bytes, zipEntryName, zipOutputStream);
            } catch (Exception e) {
                e.printStackTrace();
            }
        });
        saveFileInArchive(fileName, pathZip,zipOutputStream);
        zipOutputStream.close();
        fileOutputStream.close();
    }
    private static Map<String, byte[]> addFilesInMap(String pathZip) throws IOException {
        Map<String, byte[]> zipEntryMap = new HashMap<>();
        FileInputStream fileInputStream = new FileInputStream(pathZip);
        ZipInputStream zipInputStream = new ZipInputStream(fileInputStream);
        ZipEntry zipEntry;
        while((zipEntry = zipInputStream.getNextEntry())!= null){
            byte[] buffer = new byte[1024];
            ByteArrayOutputStream builder = new ByteArrayOutputStream();
            int end;
            while((end = zipInputStream.read(buffer)) > 0){
                builder.write(buffer, 0, end);
            }
            zipEntryMap.put(zipEntry.getName(), builder.toByteArray());
        }
        return zipEntryMap;
    }
    private static void containAndSaveSameFiles(String pathZip, byte[] bytes, String zipEntryName, ZipOutputStream zipOutputStream) throws Exception{
//        ByteArrayOutputStream readBytes = new ByteArrayOutputStream();
        ZipEntry zipEntry2 = new ZipEntry(zipEntryName);
        zipEntry2.setSize(bytes.length);
        zipOutputStream.putNextEntry(new ZipEntry(zipEntryName));
        zipOutputStream.write(bytes);
    }
    private static void saveFileInArchive(Path fileToBeAdded, String pathToArchive, ZipOutputStream zipOutputStream) throws IOException, IOException {
        zipOutputStream.putNextEntry(new ZipEntry("new/"+fileToBeAdded.getFileName()));
        Files.copy(fileToBeAdded, zipOutputStream);
    }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM