package org.dromara.system.controller.system;

import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.dev33.satoken.annotation.SaIgnore;
import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.NotEmpty;
import lombok.RequiredArgsConstructor;
import org.dromara.common.core.domain.R;
import org.dromara.common.core.validate.QueryGroup;
import org.dromara.common.log.annotation.Log;
import org.dromara.common.log.enums.BusinessType;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.web.core.BaseController;
import org.dromara.system.domain.bo.SysOssBo;
import org.dromara.system.domain.vo.SysOssUploadVo;
import org.dromara.system.domain.vo.SysOssVo;
import org.dromara.system.service.ISysFileUploadService;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.io.*;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Date;
import java.util.List;

/**
 *  通用类
 */
@RestController
@RequiredArgsConstructor
@RequestMapping("/system/file")
public class FileUploadController extends BaseController {

    @Value("${ruoyi.profile}")
    private String profile;

    private final ISysFileUploadService fileUploadService;


    /**
     * 查询OSS对象存储列表
     */
    @SaCheckPermission("system:oss:list")
    @GetMapping("/list")
    public TableDataInfo<SysOssVo> list(@Validated(QueryGroup.class) SysOssBo bo, PageQuery pageQuery) {
        return fileUploadService.queryPageList(bo, pageQuery);
    }

    /**
     * 查询OSS对象基于id串
     *
     * @param ossIds OSS对象ID串
     */
//    @SaCheckPermission("system:oss:list")
    @SaIgnore
    @GetMapping("/listByIds/{ossIds}")
    public R<List<SysOssVo>> listByIds(@NotEmpty(message = "主键不能为空")
                                       @PathVariable Long[] ossIds) {
        List<SysOssVo> list = fileUploadService.listByIds(Arrays.asList(ossIds));
        return R.ok(list);
    }

    /**
     * 删除OSS对象存储
     *
     * @param ossIds OSS对象ID串
     */
    @SaCheckPermission("system:oss:remove")
    @Log(title = "OSS对象存储", businessType = BusinessType.DELETE)
    @DeleteMapping("/{ossIds}")
    public R<Void> remove(@NotEmpty(message = "主键不能为空")
                          @PathVariable Long[] ossIds) {
        return toAjax(fileUploadService.deleteWithValidByIds(List.of(ossIds), true));
    }

    /**
     * 通用上传（本地）
     */
    @SaIgnore
    @RequestMapping("/upload")
    @ResponseBody
    public R<SysOssUploadVo> upload(@RequestParam("file") MultipartFile file) {
        if (!file.isEmpty()) {
            String uploadImage = file.getOriginalFilename();

            // 时间格式化格式
            SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyyMMddHHmmssSSS");
            // 获取当前时间并作为时间戳给文件夹命名
            String timeStamp = simpleDateFormat.format(new Date());

            String newFileName = timeStamp + "_" + uploadImage;
            File uploadFile = new File(profile, newFileName); // 完整文件路径
            try {
                file.transferTo(uploadFile);
            }catch (Exception e){
                System.out.println(e);
            }
            SysOssVo ossId = fileUploadService.saveResult(uploadImage, newFileName, newFileName);
            SysOssUploadVo ossUploadVo=new SysOssUploadVo();
            String url = newFileName;
            ossUploadVo.setUrl(url);
            ossUploadVo.setFileName(newFileName);
            ossUploadVo.setOssId(ossId.getOssId().toString());
            return R.ok("上传成功", ossUploadVo);
        }
        return R.fail("上传失败");
    }

    @SaIgnore
    @RequestMapping("/download/{fileName}")
    public void downloadFile(@PathVariable("fileName")String fileName, HttpServletResponse response) throws Exception{
        try {
            String parentPath = profile;
            File file = new File(parentPath, fileName);
            if (!file.exists()) {
                throw new FileNotFoundException("文件不存在");
            }
            FileInputStream inputStream = new FileInputStream(file);
            //输出文件
            InputStream fis = new BufferedInputStream(inputStream);
            byte[] buffer = new byte[fis.available()];
            fis.read(buffer);
            fis.close();
            response.reset();
            //获取文件的名字再浏览器下载页面
            String name = file.getName();
            response.addHeader("Content-Disposition", "attachment;filename=" + new String(name.getBytes(), "iso-8859-1"));
            response.addHeader("Content-Length", "" + file.length());
            OutputStream out = new BufferedOutputStream(response.getOutputStream());
            response.setContentType("application/octet-stream");
            out.write(buffer);
            out.flush();
            out.close();
        } catch (FileNotFoundException e) {
            throw new FileNotFoundException("文件不存在");
        }catch (Exception e) {
            throw e;
        }
    }

    /**
     * 删除OSS本地对象存储
     *
     * @param ossId OSS对象ID
     */
    @SaCheckPermission("system:oss:remove")
    @Log(title = "OSS本地对象存储", businessType = BusinessType.DELETE)
    @DeleteMapping("/delete/{ossId}")
    public R<Void> delete(@NotEmpty(message = "主键不能为空")
                          @PathVariable Long ossId) {
        return toAjax(fileUploadService.deleteOssById(ossId));
    }

}

