源码地址:https://github.com/srikanth-lingala/zip4j
引入依赖
<dependency> <groupId>net.lingala.zip4j</groupId> <artifactId>zip4j</artifactId> <version>2.6.4</version> </dependency>
编译项目,测试路径下会出现测试用文件如下图:
创建压缩包等操作代码如下:
package com.jachs.zip.zip4j; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.util.Arrays; import java.util.List; import org.junit.jupiter.api.Test; import org.springframework.boot.test.context.SpringBootTest; import com.jachs.zip.ZipApplication; import net.lingala.zip4j.ZipFile; import net.lingala.zip4j.exception.ZipException; import net.lingala.zip4j.model.ExcludeFileFilter; import net.lingala.zip4j.model.ZipParameters; import net.lingala.zip4j.model.enums.AesKeyStrength; import net.lingala.zip4j.model.enums.CompressionMethod; import net.lingala.zip4j.model.enums.EncryptionMethod; /** * @author zhanchaohan * 添加压缩 * @see https://github.com/srikanth-lingala/zip4j */ @SpringBootTest( classes = ZipApplication.class ) public class Zip4JTest { String zipPath = Zip4JTest.class.getResource ( "/test-files" ).getPath () + File.separator + "test.zip"; //添加单文件位压缩包 @Test public void test () throws ZipException { String filePath = Zip4JTest.class.getResource ( "/test-files/after_deflate_remaining_bytes.bin" ).getPath (); new ZipFile ( zipPath ).addFile ( filePath ); //or // new ZipFile(zipPath).addFile(new File(filePath)); } //添加文件到已存在压缩包 @Test public void test1 () throws ZipException { new ZipFile ( zipPath ).addFiles ( Arrays.asList ( new File ( Zip4JTest.class.getResource ( "/test-files/file_PDF_1MB.pdf" ).getPath () ), new File ( Zip4JTest.class.getResource ( "/test-files/sample_text_large.txt" ).getPath () ) ) ); } //往已存在压缩包添加文件夹 @Test public void test2 () throws ZipException { new ZipFile ( zipPath ) .addFolder ( new File ( Zip4JTest.class.getResource ( "/test-files/sample_directory" ).getPath () ) ); } //添加指定文件夹到压缩包,过滤掉指定文件 @Test public void test3 () throws ZipException { new File ( zipPath ).delete (); String addFolder = Zip4JTest.class.getResource ( "/test-files" ).getPath (); ExcludeFileFilter excludeFileFilter = new ExcludeFileFilter () { @Override public boolean isExcluded ( File file ) { System.out.println ( file.getName () ); if ( file.getName ().equals ( "file_PDF_1MB.pdf" ) ) {//匹配文件名过滤掉 return true; } if ( file.getName ().equals ( "sample_text_large.txt" ) ) { return true; } return false; } }; ZipParameters zipParameters = new ZipParameters (); zipParameters.setExcludeFileFilter ( excludeFileFilter ); new ZipFile ( zipPath ).addFolder ( new File ( addFolder ), zipParameters ); } //流的方式添加, @Test public void test5 () throws ZipException, FileNotFoundException { new ZipFile ( "MyStream.zip" ).addStream ( new FileInputStream ( Zip4JTest.class.getResource ( "/test-files/file_PDF_1MB.pdf" ).getPath () ), new ZipParameters () ); } //补充test5 @Test public void test6 () throws ZipException { ZipParameters zipParameters = new ZipParameters (); zipParameters.setCompressionMethod ( CompressionMethod.STORE );//压缩方式 new ZipFile ( "filename.zip" ) .addFile ( Zip4JTest.class.getResource ( "/test-files/file_PDF_1MB.pdf" ).getPath (), zipParameters ); } //创建带密码的压缩包 @Test public void test7 () throws ZipException { ZipParameters zipParameters = new ZipParameters (); zipParameters.setEncryptFiles ( true ); zipParameters.setEncryptionMethod ( EncryptionMethod.AES ); // Below line is optional. AES 256 is used by default. You can override it to use AES 128. AES 192 is supported only for extracting. zipParameters.setAesKeyStrength ( AesKeyStrength.KEY_STRENGTH_256 ); List<File> filesToAdd = Arrays.asList ( new File ( Zip4JTest.class.getResource ( "/test-files/file_PDF_1MB.pdf" ).getPath () ), new File ( Zip4JTest.class.getResource ( "/test-files/sample_text1.txt" ).getPath () ) ); ZipFile zipFile = new ZipFile ( "passwordfilename.zip", "password".toCharArray () ); zipFile.addFiles ( filesToAdd, zipParameters ); } //超大压缩包切分为数个小压缩包,指定切分字节大小 @Test public void test8 () throws ZipException { new File("efilename.zip").delete (); List<File> filesToAdd = Arrays.asList ( new File (Zip4JTest.class.getResource ( "/test-archives/cen_dir_entries_diff_order_as_local_entries.zip" ).getPath ()), new File (Zip4JTest.class.getResource ( "/test-archives/jar-dir-fh-entry-size-2.jar" ).getPath ()) ); ZipFile zipFile = new ZipFile ( "efilename.zip" ); //65536最小的切分字节大小 zipFile.createSplitZipFile ( filesToAdd, new ZipParameters (), true, 65537 ); // using 10MB in this example } //同test8,加了密码 @Test public void test9() throws ZipException { ZipParameters zipParameters = new ZipParameters(); zipParameters.setEncryptFiles(true); zipParameters.setEncryptionMethod(EncryptionMethod.AES); List<File> filesToAdd = Arrays.asList( new File (Zip4JTest.class.getResource ( "/test-archives/cen_dir_entries_diff_order_as_local_entries.zip" ).getPath ()), new File (Zip4JTest.class.getResource ( "/test-archives/jar-dir-fh-entry-size-2.jar" ).getPath ()) ); ZipFile zipFile = new ZipFile("EQfilename.zip", "password".toCharArray()); zipFile.createSplitZipFile(filesToAdd, zipParameters, true, 65537); // using 10MB in this example } }
解压代码如下:
package com.jachs.zip.zip4j; import java.io.File; import java.io.IOException; import java.io.InputStream; import java.util.Arrays; import java.util.HashMap; import java.util.List; import java.util.Map; import org.junit.jupiter.api.Test; import org.springframework.boot.test.context.SpringBootTest; import com.jachs.zip.ZipApplication; import net.lingala.zip4j.ZipFile; import net.lingala.zip4j.exception.ZipException; import net.lingala.zip4j.model.FileHeader; /** * @author zhanchaohan 解压缩 * @see https://github.com/srikanth-lingala/zip4j */ @SpringBootTest( classes = ZipApplication.class ) public class unZip4JTest { String zipPath = unZip4JTest.class.getResource ( "/test-files" ).getPath () + File.separator + "test.zip"; //解压 @Test public void test () throws ZipException { new ZipFile ( "filename.zip" ).extractAll ( "/destination_directory" ); } //解压带密码压缩包 @Test public void test1 () throws ZipException { new ZipFile ( "filename.zip", "password".toCharArray () ).extractAll ( "/destination_directory" ); } //解压单文件 @Test public void test2 () throws ZipException { new ZipFile ( "filename.zip" ).extractFile ( "fileNameInZip.txt", "/destination_directory" ); } //解压指定文件夹到指定路径 @Test public void test3 () throws ZipException { new ZipFile ( "filename.zip" ).extractFile ( "folderNameInZip/", "/destination_directory" ); } //同test3指定解压密码 @Test public void test5 () throws ZipException { new ZipFile ( "filename.zip", "password".toCharArray () ).extractFile ( "fileNameInZip.txt", "/destination_directory" ); } /**** * 下面的示例将提取该文件文件名inzip.txt从zip文件到输出目录/目的地目录,并将给文件命名新文件名.txt. * 如果没有新文件名的第三个参数,将使用与zip中的文件相同的名称,在本例中为文件名inzip.txt. * 如果要提取的文件是目录,则newFileName参数将用作目录名。 */ @Test public void test6 () throws ZipException { new ZipFile ( "filename.zip", "password".toCharArray () ).extractFile ( "fileNameInZip.txt", "/destination_directory", "newfileName.txt" ); } //从压缩包中获取数据流 @Test public void test7 () throws IOException { ZipFile zipFile = new ZipFile ( "filename.zip" ); FileHeader fileHeader = zipFile.getFileHeader ( "entry_name_in_zip.txt" ); InputStream inputStream = zipFile.getInputStream ( fileHeader ); } //从压缩包中删除指定文件 @Test public void test8 () throws IOException { new ZipFile ( "filename.zip" ).removeFile ( "fileNameInZipToRemove" ); } //从压缩包中删除指定文件夹 @Test public void test9 () throws IOException { new ZipFile ( "filename.zip" ).removeFile ( "root-folder/folder1/fileNameInZipToRemove" ); } /*** * 如果要确保要删除的文件存在于zip文件中,或者在使用removeFile * API时不想将文件名作为字符串处理,则可以使用另一个重载方法,该方法接收文件头: */ @Test public void test10 () throws IOException { ZipFile zipFile = new ZipFile ( "someZip.zip" ); FileHeader fileHeader = zipFile.getFileHeader ( "fileNameInZipToRemove" ); if ( fileHeader == null ) { // file does not exist } zipFile.removeFile ( fileHeader ); } /*** * 从Zip4j的v2.5.0开始,可以从zip文件中删除多个文件和文件夹。您现在可以传入一个列表,如下代码所示: */ @Test public void test11 () throws IOException { ZipFile zipFile = new ZipFile("someZip.zip"); List<String> filesToRemove = Arrays.asList("file1.txt", "file2.txt", "some-folder/", "some-new-folder-1/somefile.pdf"); zipFile.removeFiles(filesToRemove); } //有三种方法可以使用Zip4j重命名zip文件中的条目。一种方法是传入文件头和新文件名: @Test public void test12 () throws IOException { //第一种方式 ZipFile zipFile = new ZipFile("sample.zip"); FileHeader fileHeader = zipFile.getFileHeader("entry-to-be-changed.pdf"); zipFile.renameFile(fileHeader, "new-file-name.pdf"); //第二种方式 new ZipFile("filename.zip").renameFile("entry-to-be-changed.pdf", "new-file-name.pdf"); //也可以一次更改多个文件名。在这种情况下,您必须使用映射,映射中条目的键是要更改的条目,映射的值是新文件名: Map<String, String> fileNamesMap = new HashMap<>(); fileNamesMap.put("firstFile.txt", "newFileFirst.txt"); fileNamesMap.put("secondFile.pdf", "newSecondFile.pdf"); fileNamesMap.put("some-folder/thirdFile.bin", "some-folder/newThirdFile.bin"); new ZipFile("filename.zip").renameFile("entry-to-be-changed.pdf", "new-file-name.pdf"); //要修改文件夹中的条目名,新文件名还应包含完整的父路径。例如,如果一个条目名为some-条目.pdf在文件夹some folder/some sub folder/中,将此条目名称修改为某个新条目-条目.pdf: new ZipFile("filename.zip").renameFile("some-folder/some-sub-folder/some-entry.pdf", "some-folder/some-sub-folder/new-entry.pdf"); //如果缺少父路径,则该文件将放在zip文件的根目录下。在下面的示例中,重命名文件后,一些新的-条目.pdf将存在于zip文件的根目录下,而不是某个文件夹/某个子文件夹/: new ZipFile("filename.zip").renameFile("some-folder/some-sub-folder/some-entry.pdf", "some-new-entry.pdf"); //这还提供了将条目“移动”到其他文件夹的灵活性。下面的示例将移动-条目.pdf从某个文件夹/某个子文件夹/到要移动到的文件夹/子文件夹/文件也将重命名为新文件-条目.pdf. 要移动文件,请使用相同的文件名而不是新的文件名。 new ZipFile("filename.zip").renameFile("some-folder/some-sub-folder/some-entry.pdf", "folder-to-be-moved-to/sub-folder/new-entry.pdf"); } //这与创建拆分的zip文件相反,也就是说,此功能会将拆分为多个文件的zip文件合并为单个zip文件: @Test public void test13 () throws IOException { new ZipFile("split_zip_file.zip").mergeSplitFiles(new File("merged_zip_file.zip")); } //如果split zip文件(在本例中是split)没有zip文件,此方法将引发异常_文件.zip)不是拆分的zip文件。 @Test public void test14 () throws IOException { List<FileHeader> fileHeaders = new ZipFile("zipfile.zip").getFileHeaders(); fileHeaders.stream().forEach(fileHeader -> System.out.println(fileHeader.getFileName())); } @Test public void test15 () throws IOException { //判断压缩包是否加密 new ZipFile("encrypted_zip_file.zip").isEncrypted(); //判断压缩包是否是切分的压缩包 new ZipFile("split_zip_file.zip").isSplitArchive(); //添加注释 new ZipFile("some_zip_file.zip").setComment("Some comment"); //删除注释 new ZipFile("some_zip_file.zip").setComment(""); //获取注释 new ZipFile("some_zip_file.zip").getComment(); //判断是否有效 new ZipFile("valid_zip_file.zip").isValidZipFile(); } }
源码地址:https://github.com/ZhanChaoHan/zip