package com.mini.capi.utils;

import jakarta.servlet.http.HttpServletResponse;

import java.io.*;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;

public class FileUtils {

    /**
     * 检查目录是否存在，不存在则创建
     */
    public static void checkDirExists(String dirPath) {
        File dir = new File(dirPath);
        if (!dir.exists()) {
            boolean mkdirs = dir.mkdirs();
            if (!mkdirs) {
                throw new RuntimeException("创建目录失败：" + dirPath);
            }
        }
    }

    /**
     * 保存文件到指定路径
     *
     * @param inputStream 输入流（附件流）
     * @param savePath    保存路径（含文件名）
     */
    public static void saveFile(InputStream inputStream, String savePath) {
        checkDirExists(Paths.get(savePath).getParent().toString()); // 检查父目录
        try (OutputStream os = new FileOutputStream(savePath);
             BufferedInputStream bis = new BufferedInputStream(inputStream);
             BufferedOutputStream bos = new BufferedOutputStream(os)) {
            byte[] buffer = new byte[1024 * 8];
            int len;
            while ((len = bis.read(buffer)) != -1) {
                bos.write(buffer, 0, len);
            }
            bos.flush();
        } catch (IOException e) {
            throw new RuntimeException("保存文件失败：" + savePath, e);
        }
    }

    /**
     * 获取文件大小（字节）
     */
    public static long getFileSize(File file) {
        try {
            return Files.size(file.toPath());
        } catch (IOException e) {
            throw new RuntimeException("获取文件大小失败", e);
        }
    }


    /**
     * 下载文件核心方法
     */
    public static void downloadFile(HttpServletResponse response, File file, String downloadFileName) throws Exception {
        String encodedName = URLEncoder.encode(downloadFileName, StandardCharsets.UTF_8);
        // 设置响应头
        response.setContentType("application/octet-stream");
        response.setContentLengthLong(file.length());
        response.setHeader("Content-Disposition",
                String.format("attachment; filename=\"%s\"; filename*=UTF-8''%s", encodedName, encodedName));
        response.setHeader("Cache-Control", "no-cache");
        // 流传输（自动关闭）
        try (InputStream in = new BufferedInputStream(new FileInputStream(file));
             OutputStream out = new BufferedOutputStream(response.getOutputStream())) {
            byte[] buf = new byte[4096];
            int len;
            while ((len = in.read(buf)) != -1) {
                out.write(buf, 0, len);
            }
            out.flush();
        }
    }

    // 格式化文件大小（字节转人类可读格式）
    public static String formatFileSize(long bytes) {
        if (bytes < 1024) {
            return bytes + " B";
        } else if (bytes < 1024 * 1024) {
            return String.format("%.1f KB", bytes / 1024.0);
        } else if (bytes < 1024 * 1024 * 1024) {
            return String.format("%.1f MB", bytes / (1024.0 * 1024));
        } else {
            return String.format("%.1f GB", bytes / (1024.0 * 1024 * 1024));
        }
    }
}