Created
March 14, 2021 09:20
-
-
Save xyznaveen/8f6eb525c23f3a9b816f60285f188a92 to your computer and use it in GitHub Desktop.
Java zip compression example
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import java.io.File; | |
import java.io.FileInputStream; | |
import java.io.FileNotFoundException; | |
import java.io.FileOutputStream; | |
import java.io.IOException; | |
import java.util.Stack; | |
import java.util.zip.ZipEntry; | |
import java.util.zip.ZipOutputStream; | |
public class ZipHelper { | |
public static final int BUFFER_SIZE = 1024 * 8; | |
public static final int EOF = -1; | |
public static final int OFFSET_START = 0; | |
public static final int SUBSTRING_OFFSET = 1; | |
public static final String EMPTY = ""; | |
private final File source; | |
private final ZipOutputStream zipOutputStream; | |
private final Stack<File> stackOfFilesToBeZipped; | |
public ZipHelper(File source, File destination) throws FileNotFoundException { | |
// the source file and the destination file | |
// can be a single file or a directory | |
this.source = source; | |
final FileOutputStream fileOutputStream = new FileOutputStream(destination); | |
zipOutputStream = new ZipOutputStream(fileOutputStream); | |
// the level of compression can be either of 2; ZipEntry.STORED or ZipEntry.DEFLATED | |
zipOutputStream.setLevel(ZipEntry.STORED); | |
// optional if you want to add comment to the zip file | |
// zipOutputStream.setComment("don't forget to bookmark https://techenum.com"); | |
stackOfFilesToBeZipped = new Stack<>(); | |
// count total files to be zipped | |
recursivelyAddFilesToStack(source); | |
System.out.println("there are " + stackOfFilesToBeZipped.size() + " files to be zipped."); | |
} | |
/** | |
* Start the zip operation. | |
* | |
* @throws IOException | |
*/ | |
public void zip() throws IOException { | |
while (true) { | |
// looks like we have completed our zipping task | |
if (stackOfFilesToBeZipped.empty()) { | |
zipOutputStream.close(); | |
break; | |
} | |
// pop file from satck and add to zip | |
zipFile(stackOfFilesToBeZipped.pop()); | |
} | |
} | |
/** | |
* This method recursively checks if the file is a directory or a file. | |
* We only need the files so ignores the directory if encountered any. | |
* | |
* @param file the file to be added to stack | |
*/ | |
private void recursivelyAddFilesToStack(File file) { | |
if (file.isFile()) { | |
stackOfFilesToBeZipped.add(file); | |
return; | |
} | |
File[] files = file.listFiles(); | |
if (files == null) { | |
// directory is empty | |
return; | |
} | |
for (File item : files) { | |
recursivelyAddFilesToStack(item); | |
} | |
} | |
/** | |
* Zip a single file appropriately into the destination zip file. | |
* | |
* @param file the file that should be zipped. | |
* @throws IOException | |
*/ | |
private void zipFile(File file) throws IOException { | |
String relativePath = file.getAbsolutePath().replace(source.getAbsolutePath(), EMPTY); | |
if (relativePath.isEmpty()) { | |
// relativePath will be empty for a single file | |
// so to fix that we must add only that file's filename | |
relativePath = source.getName(); | |
} else { | |
// we do not want the forward slash / | |
// so for all other path we have to trim out the first character i.e. / | |
relativePath = relativePath.substring(SUBSTRING_OFFSET); | |
} | |
ZipEntry zipEntry = new ZipEntry(relativePath); | |
zipOutputStream.putNextEntry(zipEntry); | |
// write the data to output file | |
final FileInputStream fileInputStream = new FileInputStream(file); | |
final byte[] buffer = new byte[BUFFER_SIZE]; | |
int readBytes; | |
while (true) { | |
readBytes = fileInputStream.read(buffer); | |
if (readBytes == EOF) break; | |
zipOutputStream.write(buffer, OFFSET_START, readBytes); | |
} | |
fileInputStream.close(); | |
zipOutputStream.closeEntry(); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment