java安全解压文件

方法一

public class Decompression {
    private static final Logger LOGGER = Logger.getLogger(Decompression.class);

    private static final int BUFFER = 512;

    private static final int TOO_BIG = 0x6400000;

    private static final int TOO_MANY = 1024;

    private Decompression() {

    }

    public static void zipUncompress(String inputFile, String destDirPath) {
        FileOutputStream fileOutputStream = null;
        InputStream inputStream = null;
        ZipFile zipFile = null;
        try {
            File srcFile = new File(inputFile);
            if (!srcFile.exists()) {
                throw new IOException(srcFile.getPath());
            }
            zipFile = new ZipFile(srcFile);
            Enumeration entries = zipFile.entries();
            int total = 0;
            int entriesNumber = 0;
            while (entries.hasMoreElements()) {
                ZipEntry entry = (ZipEntry) entries.nextElement();
                checkFileName(entry.getName(), destDirPath);
                int count = 0;
                if (entry.isDirectory()) {
                    if (!srcFile.mkdir()) {
                        throw new IOException();
                    }
                } else {
                    String fileName = Tools.delTimeStamp(entry.getName());
                    File targetFile = new File(destDirPath + File.separator + fileName);
                    if (!targetFile.getParentFile().exists()) {
                        if (targetFile.getParentFile().mkdirs()) {
                            throw new IOException();
                        }
                    }
                    if (!targetFile.createNewFile()) {
                        throw new IOException();
                    }
                    inputStream = zipFile.getInputStream(entry);
                    fileOutputStream = new FileOutputStream(targetFile);
                    int len;
                    byte[] buf = new byte[BUFFER];
                    while ((len = inputStream.read(buf)) != -1) {
                        total += count;
                        if (total > TOO_BIG) {
                            LOGGER.error("Zip file is too big.");
                            break;
                        }
                        fileOutputStream.write(buf, 0, len);
                    }
                    entriesNumber++;
                    if (total > TOO_BIG) {
                        LOGGER.error("Zip file is too big.");
                        break;
                    }
                    if (entriesNumber > TOO_MANY) {
                        LOGGER.error("Zip file is too many.");
                        break;
                    }
                }
            }
        } catch (IOException e) {
            LOGGER.error("IOException error.", e);
        } finally {
            closeProcess(inputFile, fileOutputStream, inputStream, zipFile);
        }
    }

    private static String checkFileName(String entryName, String intendedDir) throws IOException {
        File file = new File(intendedDir, entryName);
        String canonicalPath1 = file.getCanonicalPath();
        File intendedFile = new File(intendedDir);
        String canonicalPath2 = intendedFile.getCanonicalPath();
        if (canonicalPath1.startsWith(canonicalPath2)) {
            return canonicalPath1;
        } else {
            throw new IllegalStateException();
        }
    }

    private static void closeProcess(String inputFile, FileOutputStream fileOutputStream, InputStream inputStream,
        ZipFile zipFile) {
        try {
            if (zipFile != null) {
                zipFile.close();
            }
            if (fileOutputStream != null) {
                fileOutputStream.close();
            }
            if (inputFile != null) {
                inputStream.close();
            }
        } catch (IOException e) {
            LOGGER.error("Close error.", e);
        }
    }
}

方法二

public class Decompression {
    private static final Logger LOGGER = Logger.getLogger(Decompression.class);

    private static final int BUFFER = 512;

    private static final int TOO_BIG = 0x6400000;

    private static final int TOO_MANY = 1024;

    private Decompression() {

    }

    public static void zipUncompress(String inputFile, String destDirPath) {
        FileOutputStream fileOutputStream = null;
        InputStream inputStream = null;
        ZipFile zipFile = null;
        try {
            File srcFile = new File(inputFile);
            if (!srcFile.exists()) {
                throw new IOException(srcFile.getPath());
            }
            zipFile = new ZipFile(srcFile);
            Enumeration entries = zipFile.entries();
            int total = 0;
            int entriesNumber = 0;
            while (entries.hasMoreElements()) {
                ZipEntry entry = (ZipEntry) entries.nextElement();
                checkFileName(entry.getName(), destDirPath);
                int count = 0;
                if (entry.isDirectory()) {
                    if (!srcFile.mkdir()) {
                        throw new IOException();
                    }
                } else {
                    String fileName = Tools.delTimeStamp(entry.getName());
                    File targetFile = new File(destDirPath + File.separator + fileName);
                    if (!targetFile.getParentFile().exists()) {
                        if (targetFile.getParentFile().mkdirs()) {
                            throw new IOException();
                        }
                    }
                    if (!targetFile.createNewFile()) {
                        throw new IOException();
                    }
                    inputStream = zipFile.getInputStream(entry);
                    fileOutputStream = new FileOutputStream(targetFile);
                    int len;
                    byte[] buf = new byte[BUFFER];
                    while ((len = inputStream.read(buf)) != -1) {
                        total += count;
                        if (total > TOO_BIG) {
                            LOGGER.error("Zip file is too big.");
                            break;
                        }
                        fileOutputStream.write(buf, 0, len);
                    }
                    entriesNumber++;
                    if (total > TOO_BIG) {
                        LOGGER.error("Zip file is too big.");
                        break;
                    }
                    if (entriesNumber > TOO_MANY) {
                        LOGGER.error("Zip file is too many.");
                        break;
                    }
                }
            }
        } catch (IOException e) {
            LOGGER.error("IOException error.", e);
        } finally {
            closeProcess(inputFile, fileOutputStream, inputStream, zipFile);
        }
    }

    private static String checkFileName(String entryName, String intendedDir) throws IOException {
        File file = new File(intendedDir, entryName);
        String canonicalPath1 = file.getCanonicalPath();
        File intendedFile = new File(intendedDir);
        String canonicalPath2 = intendedFile.getCanonicalPath();
        if (canonicalPath1.startsWith(canonicalPath2)) {
            return canonicalPath1;
        } else {
            throw new IllegalStateException();
        }
    }

    private static void closeProcess(String inputFile, FileOutputStream fileOutputStream, InputStream inputStream,
        ZipFile zipFile) {
        try {
            if (zipFile != null) {
                zipFile.close();
            }
            if (fileOutputStream != null) {
                fileOutputStream.close();
            }
            if (inputFile != null) {
                inputStream.close();
            }
        } catch (IOException e) {
            LOGGER.error("Close error.", e);
        }
    }
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值