package cn.reghao.autodop.common.util;

import cn.reghao.autodop.common.util.text.FileProcessor;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.io.FileUtils;

import java.io.*;
import java.nio.file.*;
import java.nio.file.attribute.BasicFileAttributes;
import java.util.Objects;

/**
 * 文件，目录操作类（新建，删除，复制，移动，清空）
 *
 * @author reghao
 * @date 2019-08-27 21:45:08
 */
@Slf4j
public class FileOps {
    /**
     * 将目录内的文件和子目录复制到另一个目录(非当前目录或其子目录)
     *
     * @param src 要复制的目录
     * @param dst 目的目录（若不存在则新建）
     * @return
     * @date 2019-09-09 下午6:11
     */
    public static void copyDirContentToDir(String src, String dst) throws IOException {
        File srcDir = new File(src);
        if (!srcDir.exists() || srcDir.isFile()) {
            log.error("{} -> 源目录不存在", src);
            return;
        }

        File dstDir = new File(dst);
        for (File file : Objects.requireNonNull(srcDir.listFiles())) {
            if (file.isDirectory()) {
                String dirname = file.getName();
                File dstdir = new File(dst + "/" + dirname);
                FileUtils.copyDirectory(file, dstdir);
            } else {
                FileUtils.copyFileToDirectory(file, dstDir);
            }
        }
    }

    /**
     * 将目录复制到另一个目录
     *
     * @param
     * @return
     * @date 2020-01-20 下午4:24
     */
    public static void copyDirToDir(String src, String dst) throws IOException {
        File srcDir = new File(src);
        if (!srcDir.exists() || srcDir.isFile()) {
            log.error("{} -> 目录不存在", src);
            return;
        }

        String dirname = srcDir.getName();
        File dstDir = new File(dst + "/" + dirname);
        FileUtils.copyDirectory(srcDir, dstDir);
    }

    /**
     * 创建目录，若目录存在则返回
     *
     * @param src 目录绝对路径
     * @return true 创建空目录成功
     * @date 2019-08-27 下午9:52
     */
    public static boolean mkdir(String src) {
        File file = new File(src);
        if (!file.exists() && file.mkdirs()) {
            return true;
        }

        if (file.exists() && file.isDirectory()) {
            return true;
        }

        return false;
    }

    public static boolean mkdirs(File dir) {
        if (!dir.exists() && dir.mkdirs()) {
            return true;
        }

        return dir.exists() && dir.isDirectory();
    }

    /**
     * 提取一个绝对路径中的目录部分
     *
     * @param
     * @return
     * @date 2019-08-28 上午10:50
     */
    public static String dirPath(String path) {
        int index = path.lastIndexOf(File.separator);
        return path.substring(0, index);
    }

    /**
     * 遍历并处理文本文件
     *
     * @param
     * @return
     * @date 2019-09-06 下午5:12
     */
    public static void traversal(String dirPath, FileProcessor processor) {
        Path path = Paths.get(dirPath);
        try {
            Files.walkFileTree(path, new FileVisitor<Path>() {
                @Override
                public FileVisitResult preVisitDirectory(Path dir, BasicFileAttributes attrs) throws IOException {
                    return FileVisitResult.CONTINUE;
                }

                // 处理目录中的文件
                @Override
                public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException {
                    processor.process(file.toFile());

                    return FileVisitResult.CONTINUE;
                }

                @Override
                public FileVisitResult visitFileFailed(Path file, IOException exc) throws IOException {
                    log.info("无法查看 {} ", file.toString());
                    return FileVisitResult.CONTINUE;
                }

                @Override
                public FileVisitResult postVisitDirectory(Path dir, IOException exc) throws IOException {
                    return FileVisitResult.CONTINUE;
                }
            });
        } catch (IOException ioe) {
            ioe.printStackTrace();
        }
    }

    public static void eraseDir(File dir) throws IOException {
        if (!dir.exists() || dir.isFile()) {
            log.info("{} -> 目录不存在", dir.getPath());
            return;
        }
        FileUtils.cleanDirectory(dir);
    }

    /**
     * 删除文件或目录
     *
     * @param
     * @return
     * @date 2021-06-17 下午9:14
     */
    public static boolean delete(File file) {
        return FileUtils.deleteQuietly(file);
    }
}
