文件打包實現

實現邏輯
1、使用java.util.zip.ZipOutputStream構造一個壓縮流(zip)
2、將一個或多個文件構造成對應的壓縮流的條目(java.util.zip.Entry)
3、將壓縮流輸出即可。
4、若是多個文件打包則需要考慮文件同名問題。
依賴

    <dependency>
        <groupId>commons-io</groupId>
        <artifactId>commons-io</artifactId>
        <version>2.6</version>
    </dependency>

源碼

package com.zhicheng.utils;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.HashMap;
import java.util.Map;
import java.util.Map.Entry;
import java.util.zip.ZipEntry;
import java.util.zip.ZipOutputStream;

import org.apache.commons.io.IOUtils;
import org.apache.commons.lang3.ArrayUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class ZipUitls {

    private Logger           logger = LoggerFactory.getLogger(ZipUitls.class);

    /**
     * 批量壓縮文件
     * 1、一般獲取文件都是在該方法中直接下載,不會直接是使用map傳入
     * @param fileIns
     * @param fileName
     * @return
     * @throws IOException
     */
    public static InputStream compress2ZipBatch(Map<File,InputStream> fileIns) throws IOException{
        if(fileIns.isEmpty()) {
            throw new IllegalArgumentException("the param fileIns can not be empty!");
        }
        //處理文件名相同情況
        Map<String,Integer> fileNameMap = new HashMap<String,Integer>();
        // 文件緩存輸出流
        ByteArrayOutputStream byteCache = new ByteArrayOutputStream();
        // 壓縮流
        ZipOutputStream zipOutStream = new ZipOutputStream(byteCache);
        try {
            for(Entry<File,InputStream> entry:fileIns.entrySet()) {
                addZipEntry(zipOutStream, entry.getValue(), dealSameFileName(fileNameMap,entry.getKey().getName()));
            }
        }finally {
            IOUtils.closeQuietly(zipOutStream);
        }
        return new ByteArrayInputStream(byteCache.toByteArray());
    }

    /**
     * 壓縮單個文件
     * @param in
     * @param fileName
     * @return
     * @throws IOException
     */
    public static InputStream compress2Zip(InputStream in,String fileName) throws IOException {
        // 文件輸出流
        ByteArrayOutputStream byteCache = new ByteArrayOutputStream();
        // 壓縮流
        ZipOutputStream zipOutStream = new ZipOutputStream(byteCache);
        addZipEntry(zipOutStream,in,fileName);
        return new ByteArrayInputStream(byteCache.toByteArray());
    }

    //添加條目
    private static void addZipEntry(ZipOutputStream zos, InputStream in, String fileName) throws IOException{
        try {
            zos.putNextEntry(new ZipEntry(fileName));
            zos.write(IOUtils.toByteArray(in));
            zos.closeEntry();
        }finally {
            IOUtils.closeQuietly(in);
        }
    }

    /**
     * 處理同一包中同名文件
     * 相同的文件名後&後綴前遞增加(n)
     * @param fileNameMap
     * @param fileName
     * @return
     */
    private static String dealSameFileName(Map<String,Integer> fileNameMap,String fileName) {
        String _fileName = fileName.substring(0,fileName.lastIndexOf("."));
        String suffix = fileName.substring(fileName.lastIndexOf(".")+1);
        if(fileNameMap.containsKey(fileName)) {
            Integer size = fileNameMap.get(fileName);
            fileNameMap.put(fileName, size.intValue()+1);
            return _fileName+"("+size.intValue()+")."+suffix;
        }else {
            fileNameMap.put(fileName, 1);
            return fileName;
        }
    }

    /**
     * 測試
     * @param args
     * @throws IOException
     */
    public static void main(String[] args) throws IOException {
        File[] files = new File("D:\\Oss_file\\pdfTest").listFiles();
        if(ArrayUtils.isNotEmpty(files)) {
            Map<File,InputStream> insMap = new HashMap<File,InputStream>();
            for(File file:files) {
                if(file.isFile()) {
                    insMap.put(file,new FileInputStream(file));
                }
            }
            OutputStream out = new FileOutputStream("D:\\Oss_file\\pdfTest\\test\\file.zip");
            IOUtils.copy(compress2ZipBatch(insMap), out);
            IOUtils.closeQuietly(out);
        }
        System.out.println("執行完成!");

    }
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章