/* * Copyright (C) 2009 eXo Platform SAS. * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU Lesser General Public License as * published by the Free Software Foundation; either version 2.1 of * the License, or (at your option) any later version. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this software; if not, write to the Free * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA * 02110-1301 USA, or see the FSF site: http://www.fsf.org. */ package org.exoplatform.services.compress; import org.exoplatform.commons.utils.PrivilegedFileHelper; import org.exoplatform.services.log.ExoLogger; import org.exoplatform.services.log.Log; import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileFilter; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import java.util.ArrayList; import java.util.List; import java.util.jar.JarEntry; import java.util.jar.JarOutputStream; import java.util.zip.ZipEntry; import java.util.zip.ZipOutputStream; /** * Created by The eXo Platform SAS Author : Chung Nguyen * nguyenchung136@yahoo.com Feb 10, 2006 */ public class CompressData { /** * The logger */ private static final Log LOG = ExoLogger.getLogger("exo.kernel.component.common.CompressData"); private String base_; private List<DataInstance> datas_ = new ArrayList<DataInstance>(); protected static final int EOF = -1; protected static final int BUFFER = 2048; public CompressData() { } public CompressData(String base) { base_ = base; } public String getBase() { return base_; } public void addFile(String entryName, File file) { try { InputStream is = PrivilegedFileHelper.fileInputStream(file); datas_.add(new InputStreamDataInstance(entryName, is)); } catch (FileNotFoundException e) { LOG.error(e.getLocalizedMessage(), e); } } public void addDir(File srcDir) { if (srcDir.isFile()) { addFile(srcDir.getName(), srcDir); } else { datas_.add(new FileDataInstance(srcDir.getName(), srcDir)); } // create recursive loop to go through all files in the srcDir..... } public void addInputStream(String entryName, InputStream is) throws Exception { datas_.add(new InputStreamDataInstance(entryName, is)); } public void createZipFile(String fileName) throws Exception { File fileZip = new File(fileName + ".zip"); FileOutputStream out = PrivilegedFileHelper.fileOutputStream(fileZip); ZipOutputStream zos = new ZipOutputStream(out); int size = datas_.size(); byte InputData[] = new byte[BUFFER]; if (size < 0) { throw new Exception("Data size is null"); } for (int i = 0; i < size; i++) { DataInstance di = datas_.get(i); if (di instanceof InputStreamDataInstance) { InputStream is = di.getInputStream(); zos.putNextEntry(new ZipEntry(di.getEntryName())); int len; while ((len = is.read(InputData)) != EOF) { zos.write(InputData, 0, len); } zos.closeEntry(); } else if (di instanceof FileDataInstance) { di.getZipOut(true, zos); } } zos.close(); out.close(); } public void createZip(OutputStream os) throws Exception { int size = datas_.size(); ZipOutputStream zos = new ZipOutputStream(os); if (size == 0) throw new Exception("Data is null"); for (int i = 0; i < size; i++) { DataInstance di = datas_.get(i); if (di instanceof InputStreamDataInstance) { InputStream is = di.getInputStream(); zos.putNextEntry(new ZipEntry(di.getEntryName())); int len; byte InputData[] = new byte[BUFFER]; while ((len = is.read(InputData)) != EOF) { zos.write(InputData, 0, len); } zos.closeEntry(); } else if (di instanceof FileDataInstance) { di.setType("Zip"); InputStream is = di.getInputStream(); int len; byte[] data = new byte[BUFFER]; while ((len = is.read(data)) != EOF) { os.write(data, 0, len); } is.close(); } } zos.close(); os.close(); } public void createJarFile(String fileName) throws Exception { File fileZip = new File(fileName + ".jar"); FileOutputStream out = PrivilegedFileHelper.fileOutputStream(fileZip); JarOutputStream jos = new JarOutputStream(out); int size = datas_.size(); if (size < 0) throw new Exception("Data size is null"); for (int i = 0; i < size; i++) { DataInstance di = datas_.get(i); if (di instanceof InputStreamDataInstance) { String entryName = di.getEntryName(); InputStream is = di.getInputStream(); jos.putNextEntry(new ZipEntry(entryName)); int len; byte InputData[] = new byte[BUFFER]; while ((len = is.read(InputData)) != EOF) { jos.write(InputData, 0, len); } jos.closeEntry(); } else if (di instanceof FileDataInstance) { di.getJarOut(true, jos); } } jos.close(); out.close(); } public void createJar(OutputStream os) throws Exception { int size = datas_.size(); JarOutputStream jos = new JarOutputStream(os); if (size == 0) throw new Exception("Data is null"); for (int i = 0; i < size; i++) { DataInstance di = datas_.get(i); if (di instanceof InputStreamDataInstance) { InputStream is = di.getInputStream(); jos.putNextEntry(new ZipEntry(di.getEntryName())); int len; byte InputData[] = new byte[BUFFER]; while ((len = is.read(InputData)) != EOF) { jos.write(InputData, 0, len); } jos.closeEntry(); is.close(); } else if (di instanceof FileDataInstance) { di.setType("Jar"); InputStream is = di.getInputStream(); int len; byte[] data = new byte[BUFFER]; while ((len = is.read(data)) != EOF) { os.write(data, 0, len); } is.close(); } } jos.close(); os.close(); } public void cleanDataInstance() { int count = datas_.size(); for (int i = 0; i < count; i++) { datas_.remove(i); } } abstract public static class DataInstance { protected String entryName_; protected String typeZip_; abstract public InputStream getInputStream(); abstract public void getJarOut(boolean containParent, JarOutputStream jos) throws Exception; abstract public void getZipOut(boolean containParent, ZipOutputStream zos) throws Exception; public String getEntryName() { return entryName_; } public void setType(String typeZip) { typeZip_ = typeZip; } public String getType() { return typeZip_; } } public static class FileDataInstance extends DataInstance { private File file_; public FileDataInstance(String entryName, File file) { entryName_ = entryName; file_ = file; } @Override public InputStream getInputStream() { ByteArrayOutputStream baos = new ByteArrayOutputStream(); if (getType().equals("Zip")) { ZipOutputStream zos = new ZipOutputStream(baos); try { getZipOut(true, zos); } catch (Exception e) { LOG.error(e.getLocalizedMessage(), e); } } else { JarOutputStream jos; try { jos = new JarOutputStream(baos); getJarOut(true, jos); } catch (Exception e) { LOG.error(e.getLocalizedMessage(), e); } } InputStream is = new ByteArrayInputStream(baos.toByteArray()); try { baos.close(); } catch (IOException e) { LOG.error(e.getLocalizedMessage(), e); } return is; } @Override public void getJarOut(boolean containParent, JarOutputStream jos) throws Exception { String path = file_.getAbsolutePath(); InputStream bufInput = null; List<File> list = listFile(file_); if (file_.isDirectory()) list.remove(file_); if (list == null || list.size() < 1) throw new Exception("nothing in the list"); for (File f : list) { StringBuilder filePath = new StringBuilder(f.getAbsolutePath()); if (f.getAbsolutePath().startsWith(path)) { if (containParent && file_.isDirectory()) { filePath = new StringBuilder(file_.getName()); filePath.append(File.separator); filePath.append(f.getAbsolutePath().substring(path.length() + 1)); } else if (file_.isDirectory()) { filePath = new StringBuilder(f.getAbsolutePath().substring(path.length() + 1)); } else { filePath = new StringBuilder(file_.getName()); } } if (f.isFile()) { bufInput = PrivilegedFileHelper.fileInputStream(f); } else { filePath.append("/"); } addToArchive(jos, bufInput, filePath.toString()); } } private List<File> listFile(File dir) { final List<File> list = new ArrayList<File>(); if (dir.isFile()) { list.add(dir); return list; } dir.listFiles(new FileFilter() { public boolean accept(File f) { if (f.isDirectory()) list.addAll(listFile(f)); list.add(f); return true; } }); return list; } public ZipOutputStream addToArchive(ZipOutputStream zipOutput, InputStream input, String entryName1) throws Exception { byte data[] = new byte[BUFFER]; ZipEntry entry = new ZipEntry(entryName1); zipOutput.putNextEntry(entry); if (input != null) { int count; while ((count = input.read(data, 0, BUFFER)) != EOF) zipOutput.write(data, 0, count); } zipOutput.closeEntry(); return zipOutput; } public JarOutputStream addToArchive(JarOutputStream jarOutput, InputStream input, String entryName1) throws Exception { byte data[] = new byte[BUFFER]; JarEntry entry = new JarEntry(entryName1); jarOutput.putNextEntry(entry); if (input != null) { int count; while ((count = input.read(data, 0, BUFFER)) != EOF) jarOutput.write(data, 0, count); } jarOutput.closeEntry(); return jarOutput; } @Override public void getZipOut(boolean containParent, ZipOutputStream zos) throws Exception { String path = file_.getAbsolutePath(); InputStream bufInput = null; List<File> list = listFile(file_); if (file_.isDirectory()) list.remove(file_); if (list == null || list.size() < 1) throw new Exception("nothing in the list"); for (File f : list) { StringBuilder filePath = new StringBuilder(f.getAbsolutePath()); if (f.getAbsolutePath().startsWith(path)) { if (containParent && file_.isDirectory()) { filePath = new StringBuilder(file_.getName()); filePath.append(File.separator); filePath.append(f.getAbsolutePath().substring(path.length() + 1)); } else if (file_.isDirectory()) { filePath = new StringBuilder(f.getAbsolutePath().substring(path.length() + 1)); } else { filePath = new StringBuilder(file_.getName()); } } if (f.isFile()) { bufInput = new FileInputStream(f); } else { filePath.append("/"); } addToArchive(zos, bufInput, filePath.toString()); } } } public static class InputStreamDataInstance extends DataInstance { private InputStream is_; public InputStreamDataInstance(String entryName, InputStream is) { entryName_ = entryName; is_ = is; } @Override public InputStream getInputStream() { return is_; } @Override public void getJarOut(boolean containParent, JarOutputStream jos) throws Exception { } @Override public void getZipOut(boolean containParent, ZipOutputStream zos) throws Exception { } } }