package com.googlecode.mycontainer.commons.util; import java.io.File; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.net.MalformedURLException; import java.net.URL; import java.util.ArrayList; import java.util.List; import java.util.zip.ZipEntry; import java.util.zip.ZipInputStream; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import com.googlecode.mycontainer.commons.io.IOUtil; public class ZipUtilExtract implements ZipProcessor { private static final Logger LOG = LoggerFactory .getLogger(ZipUtilExtract.class); private File target; private byte[] buffer = new byte[1024 * 1024]; private int reunzip = 0; private final List<String> reunzipMatches = new ArrayList<String>(); public ZipUtilExtract() { reunzipMatches.add("^.*\\.zip$"); reunzipMatches.add("^.*\\-ejb.*SNAPSHOT\\.jar$"); reunzipMatches.add("^.*\\-ejb\\.jar$"); reunzipMatches.add("^.*\\.war$"); reunzipMatches.add("^.*\\.ear$"); reunzipMatches.add("^.*\\.rar$"); } public List<String> getReunzipMatches() { return reunzipMatches; } public ZipUtilExtract target(File target) { if (!target.exists()) { if (!target.mkdirs()) { throw new RuntimeException("it can not be created: " + target); } } if (!target.isDirectory()) { throw new RuntimeException("it should be a directory: " + target); } this.target = target; return this; } public void process(ZipEntry entry, ZipInputStream in) { String name = entry.getName(); if (name == null) { throw new RuntimeException("name is required: " + entry); } boolean isDirectory = entry.isDirectory(); if (isDirectory) { unzipDirectory(name); } else { unzipFile(name, in); } } protected File unzipFile(String name, ZipInputStream in) { File f = new File(target, name); if (reunzip > 0 && reunzipMatches(name)) { int reunzip = this.reunzip - 1; LOG.info("Reunzip: " + f + " (" + reunzip + ")"); ZipUtilExtract.withTarget(f).reunzip(reunzip - 1) .unzip(new ZipInputStream(in)); return f; } FileOutputStream out = null; try { f.getParentFile().mkdirs(); out = new FileOutputStream(f); IOUtil.copyAll(in, out, buffer); } catch (FileNotFoundException e) { throw new RuntimeException(e); } finally { IOUtil.close(out); } return f; } private ZipUtilExtract unzip(ZipInputStream in) { return ZipUtil.process(in, this); } private boolean reunzipMatches(String name) { for (String check : reunzipMatches) { if (name.matches(check)) { return true; } } return false; } protected File unzipDirectory(String name) { File create = new File(target, name); if (create.exists() && create.isDirectory()) { return create; } if (!create.mkdirs()) { throw new RuntimeException("it can not be created: " + create); } return create; } public static ZipUtilExtract withTarget(File target) { return new ZipUtilExtract().target(target); } public ZipUtilExtract unzip(URL url) { LOG.info("Unzip: " + url + " (" + reunzip + ")"); return ZipUtil.process(url, this); } public ZipUtilExtract reunzip(int reunzip) { this.reunzip = reunzip; return this; } public static void main(String[] args) { File zip = new File(args[0]); File target = new File(args[1]); int reunzip = Integer.parseInt(args[2]); boolean doit = "true".equals(args[3]); System.out.println("unzip: " + zip); System.out.println("to: " + target); System.out.println("reunzip: " + reunzip); System.out.println("doit: " + doit); if (!doit) { return; } ZipUtilExtract.withTarget(target).reunzip(reunzip).unzip(zip); } private ZipUtilExtract unzip(File zip) { try { return unzip(zip.toURI().toURL()); } catch (MalformedURLException e) { throw new RuntimeException(e); } } }