package marubinotto.util;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileFilter;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.List;
import org.apache.commons.io.FileUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.tools.zip.ZipEntry;
import org.apache.tools.zip.ZipFile;
import org.apache.tools.zip.ZipOutputStream;
public class ZipUtils {
private static Log logger = LogFactory.getLog(ZipUtils.class);
// Write
public static void zipDirectory(String namePrefix, File baseDir,
FileFilter fileFilter, File zipFile, String nameEncoding)
throws IOException {
Assert.Arg.notNull(baseDir, "baseDir");
Assert.Arg.notNull(fileFilter, "fileFilter");
Assert.Arg.notNull(zipFile, "zipFile");
Assert.Arg.notNull(nameEncoding, "nameEncoding");
OutputStream output = FileUtils.openOutputStream(zipFile);
try {
zipDirectory(namePrefix, baseDir, fileFilter, output, nameEncoding);
}
finally {
output.close();
}
}
public static void zipDirectory(String namePrefix, File baseDir,
FileFilter fileFilter, OutputStream output, String nameEncoding)
throws IOException {
Assert.Arg.notNull(baseDir, "baseDir");
Assert.Arg.notNull(fileFilter, "fileFilter");
Assert.Arg.notNull(output, "output");
Assert.Arg.notNull(nameEncoding, "nameEncoding");
ZipOutputStream zipOut = new ZipOutputStream(output);
try {
zipOut.setEncoding(nameEncoding);
appendDirectory(namePrefix, baseDir, baseDir, fileFilter, zipOut);
}
finally {
zipOut.close();
}
}
public static void appendDirectory(String namePrefix, File baseDir,
File targetDir, FileFilter fileFilter, ZipOutputStream zipOut)
throws IOException {
Assert.Arg.notNull(baseDir, "baseDir");
Assert.Arg.notNull(targetDir, "targetDir");
Assert.Arg.notNull(fileFilter, "fileFilter");
Assert.Arg.notNull(zipOut, "zipOut");
File[] files = targetDir.listFiles(fileFilter);
if (files == null) { // null if security restricted
throw new IOException("Failed to list contents of " + targetDir);
}
for (int i = 0; i < files.length; i++) {
if (files[i].isDirectory()) {
appendDirectory(namePrefix, baseDir, files[i], fileFilter, zipOut);
}
else {
appendFile(namePrefix, baseDir, files[i], zipOut);
}
}
}
public static void appendFile(String namePrefix, File baseDir, File file,
ZipOutputStream zipOut) throws IOException {
Assert.Arg.notNull(baseDir, "baseDir");
Assert.Arg.notNull(file, "file");
Assert.Arg.notNull(zipOut, "zipOut");
if (namePrefix == null) namePrefix = "";
String path = FileSystemUtils.getRelativePath(baseDir, file);
ZipEntry zipEntry = new ZipEntry(namePrefix + path);
zipOut.putNextEntry(zipEntry);
InputStream fileInput = FileUtils.openInputStream(file);
try {
org.apache.commons.io.IOUtils.copyLarge(fileInput, zipOut);
}
finally {
fileInput.close();
}
}
// Read
public static boolean isZip(File file) throws IOException {
Assert.Arg.notNull(file, "file");
ZipFile zipFile = null;
try {
zipFile = new ZipFile(file);
}
catch (Exception e) {
logger.info("Not zip: " + e.toString());
return false;
}
finally {
if (zipFile != null) zipFile.close();
}
return true;
}
public static boolean containsEntry(File zipFilePath, String name,
String nameEncoding) throws IOException {
Assert.Arg.notNull(zipFilePath, "zipFilePath");
Assert.Arg.notNull(name, "name");
Assert.Arg.notNull(nameEncoding, "nameEncoding");
ZipFile zipFile = new ZipFile(zipFilePath, nameEncoding);
ZipEntry entry = zipFile.getEntry(name);
zipFile.close();
return entry != null;
}
@SuppressWarnings("rawtypes")
public static List<String> getEntryNames(File zipFilePath, String nameEncoding)
throws IOException {
Assert.Arg.notNull(zipFilePath, "zipFilePath");
Assert.Arg.notNull(nameEncoding, "nameEncoding");
List<String> names = new ArrayList<String>();
ZipFile zipFile = new ZipFile(zipFilePath, nameEncoding);
for (Enumeration e = zipFile.getEntries(); e.hasMoreElements();) {
ZipEntry entry = (ZipEntry) e.nextElement();
names.add(entry.getName());
}
zipFile.close();
return names;
}
@SuppressWarnings("rawtypes")
public static void extract(File zipFilePath, String namePrefix,
String nameEncoding, EntryReader entryReader) throws Exception {
Assert.Arg.notNull(zipFilePath, "zipFilePath");
Assert.Arg.notNull(nameEncoding, "nameEncoding");
Assert.Arg.notNull(entryReader, "entryReader");
ZipFile zipFile = new ZipFile(zipFilePath, nameEncoding);
try {
for (Enumeration e = zipFile.getEntries(); e.hasMoreElements();) {
ZipEntry entry = (ZipEntry) e.nextElement();
if (entry.isDirectory()) {
continue;
}
// File name
String fileName = entry.getName();
if (namePrefix != null) {
if (!entry.getName().startsWith(namePrefix)) {
continue;
}
fileName = fileName.substring(namePrefix.length());
}
// Output
InputStream input = zipFile.getInputStream(entry);
try {
entryReader.readEntry(fileName, input);
}
finally {
input.close();
}
}
}
finally {
if (zipFile != null) zipFile.close();
}
}
public static interface EntryReader {
public void readEntry(String name, InputStream input) throws Exception;
}
public static class Directory implements EntryReader {
private File directory;
public Directory(File directory) {
Assert.Arg.notNull(directory, "directory");
this.directory = directory;
}
public void readEntry(String name, InputStream input) throws Exception {
File file = new File(this.directory, name);
OutputStream output = new BufferedOutputStream(
FileUtils.openOutputStream(file));
try {
org.apache.commons.io.IOUtils.copy(input, output);
}
finally {
output.close();
}
}
}
}