SpringBoot decompresses ZIP, 7Z, RAR5 (compatible with RAR4)

These three decompressions are the needs I encountered at work. They were finally completed after a day of searching and sorting.

The method in this article can be used in a production environment. Due to business requirements, my method returns the decompressed file name. You can change the return value according to your own needs.

Assign the file encoding to prevent the file name and file content from being garbled after the file is decompressed. This has indeed happened to me, so I have learned a lesson.

private static final String CHINESE_CHARSET = "GBK";

Extract ZIP

In the code, zipFilePath is the location of the compressed file and destDir is the location after decompression.

Import dependencies

<dependency>
    <groupId>org.apache.ant</groupId>
    <artifactId>ant</artifactId>
    <version>1.9.6</version>
</dependency>

code

private List<String> unzip(String zipFilePath, String destDir) {
        List<String> nameList = new ArrayList<>();
        ZipFile zipFile = null;
        try {
            BufferedInputStream bis = null;
            FileOutputStream fos = null;
            BufferedOutputStream bos = null;
            zipFile = new ZipFile(zipFilePath, CHINESE_CHARSET);
            Enumeration<ZipEntry> zipEntries = zipFile.getEntries();
            File file, parentFile;
            ZipEntry entry;
            byte[] cache = new byte[1024];

            while (zipEntries.hasMoreElements()) {
                entry = (ZipEntry) zipEntries.nextElement();
                if (entry.isDirectory()) {
                    new File(destDir + entry.getName()).mkdirs();
                    continue;
                }
                bis = new BufferedInputStream(zipFile.getInputStream(entry));
                long time = System.currentTimeMillis();
                file = new File(destDir + time + "_" + entry.getName());
                //Get file name
                String fileName = file.getName()
                nameList.add(fileName);
                parentFile = file.getParentFile();
                if (parentFile != null & amp; & amp; (!parentFile.exists())) {
                    parentFile.mkdirs();
                }
                fos = new FileOutputStream(file);
                bos = new BufferedOutputStream(fos, 1024);
                int readIndex = 0;
                while ((readIndex = bis.read(cache, 0, 1024)) != -1) {
                    fos.write(cache, 0, readIndex);
                }
                bos.flush();
                bos.close();
                fos.close();
                bis.close();
            }
        } catch (IOException e) {
            e.printStackTrace();
            return new ArrayList<>();
        }finally{
            try {
                zipFile.close();
            } catch (IOException e) {
                e.printStackTrace();
                return new ArrayList<>();
            }
        }
        return nameList;
    }

Unzip 7Z

Import dependencies

<dependency>
    <groupId>net.sf.sevenzipjbinding</groupId>
    <artifactId>sevenzipjbinding</artifactId>
    <version>16.02-2.01</version>
</dependency>

code

private List<String> un7z(String zipFilePath, String destDir){
        List<String> nameList = new ArrayList<>();
        SevenZFile zIn = null;
        try {
            File file = new File(zipFilePath);
            zIn = new SevenZFile(file);
            SevenZArchiveEntry entry = null;
            File newFile = null;
            long time = System.currentTimeMillis();
            while ((entry = zIn.getNextEntry()) != null){
                //Decompress if it is not a folder
                if(!entry.isDirectory()){
                    newFile = new File(destDir,time + "_" + entry.getName());
                    String fileName = newFile.getName();
                    nameList.add(fileName);
                    if(!newFile.exists()){
                        new File(newFile.getParent()).mkdirs(); //Create the upper directory of this file
                    }
                    OutputStream out = new FileOutputStream(newFile);
                    BufferedOutputStream bos = new BufferedOutputStream(out);
                    int len = -1;
                    byte[] buf = new byte[(int)entry.getSize()];
                    while ((len = zIn.read(buf)) != -1){
                        bos.write(buf, 0, len);
                    }
                    bos.flush();
                    bos.close();
                    out.close();
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
            return new ArrayList<>();
        }finally {
            try {
                if (zIn != null){
                    zIn.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
                return new ArrayList<>();
            }
        }

        return nameList;
    }

Extract rar

Personally, I think decompressing RAR is the most difficult, because RAR5 decompression is not open source, so it requires a lot of other operations. Please spend some time understanding how to operate the specific code.

Import dependencies

<dependency>
    <groupId>com.github.axet</groupId>
    <artifactId>java-unrar</artifactId>
    <version>1.7.0-8</version>
</dependency>

First, to decompress rar, you need to create a tool class ExtractCallback

public class ExtractCallback implements IArchiveExtractCallback {

    private int index;
    private IInArchive inArchive;
    private String ourDir;
    private List<String> nameList = new ArrayList<>();

    public ExtractCallback(IInArchive inArchive, String ourDir) {
        this.inArchive = inArchive;
        this.ourDir = ourDir;
    }

    @Override
    public ISequentialOutStream getStream(int index, ExtractAskMode extractAskMode)throws SevenZipException {
        this.index = index;
        final String path = (String) inArchive.getProperty(index, PropID.PATH);
        final boolean isFolder = (boolean) inArchive.getProperty(index,PropID.IS_FOLDER);
        final String[] oldPath = {""};
        long time = System.currentTimeMillis();
        return new ISequentialOutStream() {
            @Override
            public int write(byte[] data) throws SevenZipException {
                try {
                    if (!isFolder) {
                        File file = new File(ourDir + time + "_" + path);
                        final String fileName = file.getName();
                        int i = nameList.indexOf(fileName);
                        if (i==-1){
                            nameList.add(fileName);
                        }
                        if (path.equals(oldPath[0])) {
                            save2File(file, data, true);
                        } else {
                            save2File(file, data, false);
                        }
                        oldPath[0] = path;
                    }
                } catch (Exception e) {
                    e.printStackTrace();
                    nameList = new ArrayList<>();
                }
                return data.length;
            }
        };
    }

    @Override
    public void prepareOperation(ExtractAskMode extractAskMode) throws SevenZipException {

    }

    @Override
    public void setOperationResult(ExtractOperationResult extractOperationResult) throws SevenZipException {

    }

    @Override
    public void setTotal(long l) throws SevenZipException {

    }

    @Override
    public void setCompleted(long l) throws SevenZipException {

    }

    public boolean save2File(File file, byte[] msg, boolean append) {
        FileOutputStream fos = null;
        try {
            File parent = file.getParentFile();
            boolean bool;
            if ((!parent.exists()) & amp; & amp; (!parent.mkdirs())) {
                return false;
            }
            fos = new FileOutputStream(file, append);
            fos.write(msg);
            fos.flush();
            return true;
        } catch (Exception e) {
            e.printStackTrace();
            return false;
        } finally {
            if (fos != null) {
                try {
                    fos.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    public List<String> getNameList() {
        return nameList;
    }

    public void setNameList(List<String> nameList) {
        this.nameList = nameList;
    }
}

Use the unrar method to call the tool class to decompress. The unrar method passes in the parameter rarFile as the compressed file, and dstDirectoryPath as the decompressed file location. In fact, whether it is a compressed file or a compressed file location, the essence is the same. You need to find this Decompress the compressed file

Implement code

public static List<String> unRar(File rarFile,String dstDirectoryPath){
        IInArchive archive;
        RandomAccessFile randomAccessFile;
        try {
            randomAccessFile = new RandomAccessFile(rarFile,"r");
            archive = SevenZip.openInArchive(null,new RandomAccessFileInStream(randomAccessFile));
            int[] in = new int[archive.getNumberOfItems()];
            for (int i = 0; i < in.length; i + + ) {
                in[i] = i;
            }
            final ExtractCallback extractCallback = new ExtractCallback(archive, dstDirectoryPath);
            archive.extract(in,false,extractCallback);
            archive.close();
            randomAccessFile.close();
            return extractCallback.getNameList();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }

This article is shared here. I share this article because I want to save it so that when I encounter such needs in the future, I don’t have to search hard. I hope this article can help you. Since it is my first time to share it, the writing style Or the code may be unclear or flawed. Please forgive me and correct me. Thank you.

The knowledge points of the article match the official knowledge files, and you can further learn related knowledge. Java Skill TreeHomepageOverview 138777 people are learning the system