package com.yunzhupaas.base.controller;

import cn.dev33.satoken.annotation.SaCheckPermission;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.Parameters;
import io.swagger.v3.oas.annotations.tags.Tag;
import jakarta.validation.Valid;
import com.yunzhupaas.base.ActionResult;
import com.yunzhupaas.base.entity.DictionaryDataEntity;
import com.yunzhupaas.base.entity.PrintDevEntity;
import com.yunzhupaas.base.entity.PrintVersionEntity;
import com.yunzhupaas.base.model.print.*;
import com.yunzhupaas.base.model.query.PrintDevDataQuery;
import com.yunzhupaas.base.model.query.PrintDevParam;
import com.yunzhupaas.base.model.vo.PrintDevListVO;
import com.yunzhupaas.base.model.vo.PrintDevVO;
import com.yunzhupaas.base.service.DictionaryDataService;
import com.yunzhupaas.base.service.PrintDevService;
import com.yunzhupaas.base.service.PrintVersionService;
import com.yunzhupaas.base.vo.DownloadVO;
import com.yunzhupaas.base.vo.ListVO;
import com.yunzhupaas.base.vo.PageListVO;
import com.yunzhupaas.base.vo.PaginationVO;
import com.yunzhupaas.config.ConfigValueUtil;
import com.yunzhupaas.constant.MsgCode;
import com.yunzhupaas.emnus.ModuleTypeEnum;
import com.yunzhupaas.exception.DataException;
import com.yunzhupaas.exception.WorkFlowException;
import com.yunzhupaas.permission.entity.UserEntity;
import com.yunzhupaas.permission.service.UserService;
import com.yunzhupaas.util.*;
import com.yunzhupaas.util.enums.DictionaryDataEnum;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.util.*;
import java.util.stream.Collectors;

/**
 * 打印模板 -控制器
 *
 * @author 云筑产品开发平台组
 * @version V3.2.0
 * @copyright 深圳市乐程软件有限公司
 * @date 2024-09-30
 */
@Tag(name = "打印模板", description = "print")
@RestController
@RequestMapping("/api/system/printDev")
public class PrintDevController {

    @Autowired
    private PrintDevService printDevService;
    @Autowired
    private PrintVersionService versionService;
    @Autowired
    private FileExport fileExport;
    @Autowired
    private ConfigValueUtil configValueUtil;
    @Autowired
    private DictionaryDataService dictionaryDataService;
    @Autowired
    private UserService userService;

    @Operation(summary = "列表")
    @SaCheckPermission("onlineDev.printDev")
    @GetMapping
    public ActionResult list(PaginationPrint paginationPrint) {
        List<PrintDevEntity> list = printDevService.getList(paginationPrint);
        List<String> userId = list.stream().map(t -> t.getCreatorUserId()).collect(Collectors.toList());
        List<String> lastUserId = list.stream().map(t -> t.getLastModifyUserId()).collect(Collectors.toList());
        lastUserId.removeAll(Collections.singleton(null));
        List<UserEntity> userEntities = userService.getUserName(userId);
        List<UserEntity> lastUserIdEntities = userService.getUserName(lastUserId);
        List<DictionaryDataEntity> typeList = dictionaryDataService.getListByTypeDataCode(DictionaryDataEnum.SYSTEM_PRINTDEV.getDictionaryTypeId());
        List<PrintDevListVO> listVOS = new ArrayList<>();
        for (PrintDevEntity entity : list) {
            PrintDevListVO vo = JsonUtil.getJsonToBean(entity, PrintDevListVO.class);
            DictionaryDataEntity dataEntity = typeList.stream().filter(t -> t.getId().equals(entity.getCategory())).findFirst().orElse(null);
            if (dataEntity != null) {
                vo.setCategory(dataEntity.getFullName());
            } else {
                vo.setCategory("");
            }
            //创建者
            UserEntity creatorUser = userEntities.stream().filter(t -> t.getId().equals(entity.getCreatorUserId())).findFirst().orElse(null);
            vo.setCreatorUser(creatorUser != null ? creatorUser.getRealName() + "/" + creatorUser.getAccount() : entity.getCreatorUserId());
            //修改人
            UserEntity lastModifyUser = lastUserIdEntities.stream().filter(t -> t.getId().equals(entity.getLastModifyUserId())).findFirst().orElse(null);
            vo.setLastModifyUser(lastModifyUser != null ? lastModifyUser.getRealName() + "/" + lastModifyUser.getAccount() : entity.getLastModifyUserId());
            listVOS.add(vo);
        }
        PaginationVO paginationVO = JsonUtil.getJsonToBean(paginationPrint, PaginationVO.class);
        return ActionResult.page(listVOS, paginationVO);
    }

    /*============模板增删改==============*/

    @Operation(summary = "新增")
    @Parameters({
            @Parameter(name = "printDevForm", description = "打印模板数据传输对象")
    })
    @SaCheckPermission("onlineDev.printDev")
    @PostMapping
    public ActionResult create(@RequestBody @Valid PrintDevFormDTO printDevForm) {
        printDevService.create(printDevForm);
        return ActionResult.success(MsgCode.SU001.get(), printDevForm.getId());
    }

    @Operation(summary = "详情")
    @Parameters({
            @Parameter(name = "id", description = "打印模板id")
    })
    @SaCheckPermission("onlineDev.printDev")
    @GetMapping("/{id}")
    public ActionResult<PrintDevInfoVO> info(@PathVariable("id") String id) {
        PrintDevEntity byId = printDevService.getById(id);
        PrintDevInfoVO vo = JsonUtil.getJsonToBean(byId, PrintDevInfoVO.class);
        return ActionResult.success(vo);
    }

    @Operation(summary = "更新")
    @PutMapping("/{id}")
    @Parameters({
            @Parameter(name = "id", description = "主键", required = true),
            @Parameter(name = "form", description = "流程模型", required = true),
    })
    public ActionResult update(@PathVariable("id") String id, @RequestBody @Valid PrintDevFormDTO printDevForm) throws WorkFlowException {
        PrintDevEntity printDevEntity = JsonUtil.getJsonToBean(printDevForm, PrintDevEntity.class);
        PrintDevEntity originEntity = printDevService.getById(id);
        printDevService.creUpdateCheck(printDevEntity,
                !originEntity.getFullName().equals(printDevForm.getFullName()),
                !originEntity.getEnCode().equals(printDevForm.getEnCode()));
        printDevEntity.setId(id);
        printDevService.updateById(printDevEntity);
        return ActionResult.success(MsgCode.SU004.get());
    }

    @Operation(summary = "删除")
    @Parameters({
            @Parameter(name = "id", description = "打印模板id")
    })
    @SaCheckPermission("onlineDev.printDev")
    @DeleteMapping("/{id}")
    public ActionResult<PrintDevFormDTO> delete(@PathVariable String id) {
        //对象存在判断
        if (printDevService.getById(id) != null) {
            printDevService.removeById(id);
            versionService.removeByTemplateId(id);
            return ActionResult.success(MsgCode.SU003.get());
        } else {
            return ActionResult.fail(MsgCode.FA003.get());
        }
    }

    /*============版本增删改==============*/
    @Operation(summary = "版本详情")
    @Parameters({
            @Parameter(name = "versionId", description = "打印版本id")
    })
    @SaCheckPermission("onlineDev.printDev")
    @GetMapping("/Info/{versionId}")
    public ActionResult<PrintDevInfoVO> versionInfo(@PathVariable String versionId) {
        PrintDevInfoVO info = printDevService.getVersionInfo(versionId);
        return ActionResult.success(info);
    }

    @Operation(summary = "版本新增")
    @Parameters({
            @Parameter(name = "versionId", description = "打印版本id")
    })
    @SaCheckPermission("onlineDev.printDev")
    @PostMapping("/Info/{versionId}")
    public ActionResult copyVersion(@PathVariable String versionId) {
        String newVersionId = versionService.copyVersion(versionId);
        return ActionResult.success(MsgCode.SU005.get(), newVersionId);
    }

    @Operation(summary = "版本删除")
    @Parameters({
            @Parameter(name = "versionId", description = "打印版本id")
    })
    @SaCheckPermission("onlineDev.printDev")
    @DeleteMapping("/Info/{versionId}")
    public ActionResult deleteVersion(@PathVariable String versionId) {
        PrintVersionEntity byId = versionService.getById(versionId);
        if (byId != null) {
            List<PrintVersionEntity> list = versionService.getList(byId.getTemplateId());
            if (list.size() == 1) {
                return ActionResult.fail(MsgCode.SYS043.get());
            }
            if (Objects.equals(byId.getState(), 1)) {
                return ActionResult.fail(MsgCode.SYS044.get());
            }
            if (Objects.equals(byId.getState(), 2)) {
                return ActionResult.fail(MsgCode.SYS045.get());
            }
            versionService.removeById(versionId);
        }
        return ActionResult.success(MsgCode.SU003.get());
    }

    @Operation(summary = "版本列表")
    @Parameters({
            @Parameter(name = "id", description = "打印模板id")
    })
    @SaCheckPermission("onlineDev.printDev")
    @GetMapping("/Version/{id}")
    public ActionResult<List<PrintVersionListVO>> versionList(@PathVariable String id) {
        List<PrintVersionEntity> list = versionService.getList(id);
        List<PrintVersionListVO> listVO = new ArrayList<>();
        for (PrintVersionEntity jsonEntity : list) {
            PrintVersionListVO vo = JsonUtil.getJsonToBean(jsonEntity, PrintVersionListVO.class);
            vo.setFullName("打印版本V" + vo.getVersion());
            listVO.add(vo);
        }
        return ActionResult.success(listVO);
    }

    //***********************************动作start
    @Operation(summary = "保存或者发布")
    @Parameters({
            @Parameter(name = "printDevForm", description = "打印模板数据传输对象")
    })
    @SaCheckPermission("onlineDev.printDev")
    @PostMapping("/Save")
    public ActionResult saveOrRelease(@RequestBody @Valid PrintDevUpForm form) {
        printDevService.saveOrRelease(form);
        if (Objects.equals(form.getType(), 1)) {
            return ActionResult.success(MsgCode.SU011.get());
        }
        return ActionResult.success(MsgCode.SU002.get());
    }

    @Operation(summary = "复制")
    @Parameters({
            @Parameter(name = "id", description = "打印模板id")
    })
    @SaCheckPermission("onlineDev.printDev")
    @PostMapping("/{id}/Actions/Copy")
    public ActionResult<PageListVO<PrintDevEntity>> copy(@PathVariable String id) {
        printDevService.copyPrintdev(id);
        return ActionResult.success(MsgCode.SU007.get());
    }

    @Operation(summary = "导出")
    @Parameters({
            @Parameter(name = "id", description = "打印模板id")
    })
    @SaCheckPermission("onlineDev.printDev")
    @GetMapping("/{id}/Actions/Export")
    public ActionResult<DownloadVO> export(@PathVariable String id) {
        PrintDevEntity entity = printDevService.getById(id);
        List<PrintVersionEntity> list = versionService.getList(id);
        if (CollectionUtils.isEmpty(list)) {
            return ActionResult.fail(MsgCode.FA001.get());
        }
        PrintDevInfoVO info = printDevService.getVersionInfo(list.get(0).getId());
        //导出文件
        DownloadVO downloadVO = fileExport.exportFile(info, configValueUtil.getTemporaryFilePath(), entity.getFullName(), ModuleTypeEnum.SYSTEM_PRINT.getTableName());
        return ActionResult.success(downloadVO);
    }

    @Operation(summary = "导入")
    @SaCheckPermission("onlineDev.printDev")
    @PostMapping(value = "/Actions/Import", consumes = MediaType.MULTIPART_FORM_DATA_VALUE)
    public ActionResult<PageListVO<PrintDevEntity>> importData(@RequestPart("file") MultipartFile multipartFile,
                                                               @RequestParam("type") Integer type) throws DataException {
        //判断是否为.json结尾
        if (FileUtil.existsSuffix(multipartFile, ModuleTypeEnum.SYSTEM_PRINT.getTableName())) {
            return ActionResult.fail(MsgCode.IMP002.get());
        }
        //读取文件内容
        String fileContent = FileUtil.getFileContent(multipartFile);
        PrintDevInfoVO infVo = JsonUtil.getJsonToBean(fileContent, PrintDevInfoVO.class);
        String str = printDevService.importData(infVo, type);
        if (StringUtil.isNotEmpty(str)) {
            return ActionResult.fail(str);
        }
        return ActionResult.success(MsgCode.IMP001.get());
    }
    //***********************************动作end

    /**
     * 下拉列表
     *
     * @return 返回列表数据
     */
    @Operation(summary = "下拉列表")
    @GetMapping("/Selector")
    public ActionResult<ListVO<PrintDevVO>> selectorList(String category) throws Exception {
        ListVO<PrintDevVO> vo = new ListVO<>();
        vo.setList(printDevService.getTreeModel(category));
        return ActionResult.success(vo);
    }

    @Operation(summary = "Sql数据获取")
    @PostMapping("/BatchData")
    public ActionResult getBatchData(@RequestBody PrintDevDataQuery query) {
        String id = XSSEscape.escape(query.getId());
        PrintDevEntity entity = printDevService.getById(id);
        if (entity == null) {
            return ActionResult.fail(MsgCode.PRI001.get());
        }
        ArrayList<Object> list = new ArrayList<>();
        if (query.getFormInfo() != null && query.getFormInfo().size() > 0) {
            List<PrintDevParam> flowTaskInfo = query.getFormInfo();
            for (PrintDevParam rid : flowTaskInfo) {
                String oneId = "";
                String flowTaskId = "";
                if (Objects.nonNull(rid.getFormId())) {
                    oneId = XSSEscape.escape(rid.getFormId().toString());
                }
                if (Objects.nonNull(rid.getFlowTaskId())) {
                    flowTaskId = XSSEscape.escape(rid.getFlowTaskId().toString());
                }
                Map<String, Object> dataMap = printDevService.getDataMap(id, oneId, flowTaskId, query.getMap());
                dataMap.put("fullName", entity.getFullName());
                list.add(dataMap);
            }
            return ActionResult.success(list);
        }
        return ActionResult.success(list);
    }

    /**
     * 查询打印列表
     *
     * @param ids
     * @return
     */
    @Operation(summary = "查询打印列表")
    @Parameters({
            @Parameter(name = "ids", description = "主键集合")
    })
    @PostMapping("getListById")
    public List<PrintOption> getListById(@RequestBody List<String> ids) {
        return printDevService.getPrintTemplateOptions(ids);
    }

    @Operation(summary = "查询打印列表")
    @Parameters({
            @Parameter(name = "data", description = "打印模板-数查询对象")
    })
    @PostMapping("getListOptions")
    public ActionResult getListOptions(@RequestBody PrintDevDataQuery data) {
        List<String> ids = data.getIds();
        QueryWrapper<PrintDevEntity> wrapper = new QueryWrapper<>();
        wrapper.lambda().in(PrintDevEntity::getId, ids);
        List<PrintDevEntity> list = printDevService.getBaseMapper().selectList(wrapper);
        List<PrintOption> options = JsonUtil.getJsonToList(list, PrintOption.class);
        return ActionResult.success(options);
    }

    //新增

    @Operation(summary = "列表预览")
    @Parameters({
            @Parameter(name = "id", description = "打印模板id")
    })
    @SaCheckPermission("onlineDev.printDev")
    @GetMapping("/{id}/Actions/Preview")
    public ActionResult<PrintDevInfoVO> previewInfo(@PathVariable("id") String id) {
        List<PrintVersionEntity> list = versionService.getList(id);
        if (CollectionUtils.isEmpty(list)) {
            return ActionResult.fail(MsgCode.FA001.get());
        }
        PrintDevInfoVO info = printDevService.getVersionInfo(list.get(0).getId());
        PrintDevInfoVO vo = JsonUtil.getJsonToBean(info, PrintDevInfoVO.class);
        return ActionResult.success(vo);
    }

    @Operation(summary = "打印模板业务列表")
    @GetMapping("/WorkSelector")
    public ActionResult<PageListVO<PrintDevListVO>> getWorkSelector(PaginationPrint pagination) {
        List<PrintDevEntity> list = printDevService.getWorkSelector(pagination);
        List<PrintDevListVO> listVO = JsonUtil.getJsonToList(list, PrintDevListVO.class);
        PaginationVO paginationVO = JsonUtil.getJsonToBean(pagination, PaginationVO.class);
        return ActionResult.page(listVO, paginationVO);
    }


}

