package com.patzn.lims.frame.service.impl;


import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.ArrayUtils;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;

import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.google.common.collect.Lists;
import com.patzn.cloud.commons.api.RestAssert;
import com.patzn.lims.core.web.Account;
import com.patzn.lims.core.web.LoginHelper;
import com.patzn.lims.core.web.BaseServiceImpl;
import com.patzn.lims.core.oss.OssClient;
import com.patzn.lims.res.service.ILmsPropertyService;
import com.patzn.lims.frame.dto.LmsFrameProblemApproveDTO;
import com.patzn.lims.frame.entity.*;
import com.patzn.lims.frame.enums.FrameFileTypeEnum;
import com.patzn.lims.frame.enums.ProblemImproveEnum;
import com.patzn.lims.frame.mapper.LmsFrameProblemImproveMapper;
import com.patzn.lims.frame.service.ILmsFrameProblemImproveAttachmentService;
import com.patzn.lims.frame.service.ILmsFrameProblemImproveRecordService;
import com.patzn.lims.frame.service.ILmsFrameProblemImproveService;
import com.patzn.lims.frame.vo.LmsFrameProblemImproveVO;
import com.patzn.lims.sys.service.ISysUserService;
import com.patzn.lims.workflow.FlowInfo;
import com.patzn.lims.workflow.FlowProcess;
import com.patzn.lims.workflow.FlowType;
import com.patzn.lims.workflow.FlowVariables;
import com.patzn.lims.workflow.service.IFlowProcessService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * <p>
 * 改进/纠正/预防措施管理 服务实现类
 * </p>
 *
 * @author patzn
 * @since 2018-07-18
 */
@Service
public class LmsFrameProblemImproveServiceImpl extends BaseServiceImpl<LmsFrameProblemImproveMapper, LmsFrameProblemImprove> implements ILmsFrameProblemImproveService {

    @Autowired
    private ILmsFrameProblemImproveRecordService lmsFrameProblemImproveRecordService;
    @Autowired
    private ILmsPropertyService lmsPropertyService;
    @Autowired
    private ILmsFrameProblemImproveAttachmentService lmsFrameProblemImproveAttachmentService;
    @Autowired
    private OssClient ossClient;
    @Autowired
     private IFlowProcessService flowProcessClient;
    @Autowired
    private ISysUserService sysUserClient;

    @Override
    public Page<LmsFrameProblemImprove> page(Page<LmsFrameProblemImprove> page, LmsFrameProblemImprove lmsFrameProblemImprove) {
        lmsFrameProblemImprove.setTempStatus(1);
         QueryWrapper wrapper = Wrappers.query(lmsFrameProblemImprove);
        if (null != lmsFrameProblemImprove.getProblemDisplay()) {
            wrapper.like("problem_display", lmsFrameProblemImprove.getProblemDisplay());
            lmsFrameProblemImprove.setProblemDisplay(null);
        }
        if (null != lmsFrameProblemImprove.getMeasuresDisplay()) {
            wrapper.like("measures_display", lmsFrameProblemImprove.getMeasuresDisplay());
            lmsFrameProblemImprove.setMeasures(null);
        }
        wrapper.orderBy(true,true,"ctime");
        return page(page, wrapper);
    }


    @Override
    public List<LmsFrameProblemImprove> list(LmsFrameProblemImprove lmsFrameProblemImprove) {
        return list(Wrappers.query(lmsFrameProblemImprove));
    }

    @Override
    public void exportItem(HttpServletResponse response, LmsFrameProblemApproveDTO dto) {
//        RestAssert.fail(null == dto, "导出数据参数不能为空");
//        List<LmsFrameProblemApproveETO> itemList = baseMapper.selectEtoByDto(dto);
//        itemList.forEach(e -> {
//            if (e.getProblem() != null) {
//                e.setProblem(e.getProblem().replaceAll("<[.[^<]]*>", ""));
//            }
//            if (e.getMeasures() != null) {
//                e.setMeasures(e.getMeasures().replaceAll("<[.[^<]]*>", ""));
//            }
//            if (e.getStatus() != null) {
//                e.setEnStatus(e.getStatus().getDisplay());
//            }
//        });
//        if (CollectionUtils.isNotEmpty(itemList)) {
//            new LmsFrameProblemApproveExportHandler(itemList).generater(response);
//        }
    }

    @Override
    public boolean submit(Long[] ids, Account account) {
        RestAssert.fail(ArrayUtils.isEmpty(ids), "请选择待提交的改进/纠正/预防措施管理");
        int count = count(Wrappers.<LmsFrameProblemImprove>query().eq("status", 1).in("id", ids));
        RestAssert.fail(count > 0, "选择了已提交的数据请确认");
        List<LmsFrameProblemImproveRecord> recordList = Lists.newArrayList();
        for (Long id : ids) {
            LmsFrameProblemImproveRecord record = new LmsFrameProblemImproveRecord();
            record.setOrigin("草稿");
            record.setTarget("已提交");
            record.setLiable(account.getUserName());
            record.setOperator(account.getUserName());
            record.setType(1);
            record.setProblemImproveId(id);
            record.setRemark("提交");
            recordList.add(record);
        }
        if (CollectionUtils.isNotEmpty(recordList)) {
            lmsFrameProblemImproveRecordService.saveBatch(recordList);
        }
        return super.update(new LmsFrameProblemImprove().setStatus(ProblemImproveEnum.DRAFT), Wrappers.<LmsFrameProblemImprove>query().in("id", ids));
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public boolean updateFrameProblemImproveById(LmsFrameProblemImprove improve) {
        RestAssert.fail(null == improve.getId(), "编辑id不能为空");
        LmsFrameProblemImprove db = getById(improve.getId());
        String remark = lmsPropertyService.getObjectCompareDifferent(improve, db, "改进纠正预防措施管理对比", "信息修改：");
        if (StringUtils.isNotBlank(remark)) {
            LmsFrameProblemImproveRecord lmsFrameProblemImproveRecord = new LmsFrameProblemImproveRecord();
            lmsFrameProblemImproveRecord.setType(2);
            lmsFrameProblemImproveRecord.setProblemImproveId(db.getId());
            lmsFrameProblemImproveRecord.setRemark(remark);
            lmsFrameProblemImproveRecord.setLiable(LoginHelper.getAccount().getUserName());
            lmsFrameProblemImproveRecord.setOperator(LoginHelper.getAccount().getUserName());
            lmsFrameProblemImproveRecord.setOrigin("草稿");
            lmsFrameProblemImproveRecord.setTarget("草稿");
            lmsFrameProblemImproveRecordService.save(lmsFrameProblemImproveRecord);
        }
        return updateById(improve);
    }

    @Override
    public LmsFrameProblemImproveVO getTempVO() {
        LmsFrameProblemImprove entity = new LmsFrameProblemImprove();
        entity.setTempStatus(0);
        LmsFrameProblemImprove lmsFrameProblemImprove = baseMapper.selectOne(Wrappers.query(entity));
        if (null != lmsFrameProblemImprove) {
            LmsFrameProblemImproveVO vo = lmsFrameProblemImprove.convert(LmsFrameProblemImproveVO.class);
            //获取附件
            LmsFrameProblemImproveAttachment attachment = new LmsFrameProblemImproveAttachment();
            attachment.setProblemImproveId(lmsFrameProblemImprove.getId());
            List<LmsFrameProblemImproveAttachment> lmsFrameFileList = lmsFrameProblemImproveAttachmentService.list(attachment);
            lmsFrameFileList.forEach(e -> {
                e.setObjectKey(ossClient.getUrl(e.getObjectKey()).toString());
            });
            vo.setLmsFrameProblemImproveAttachments(lmsFrameFileList);
            return vo;
        }
        LmsFrameProblemImprove plan = new LmsFrameProblemImprove();
        plan.setTempStatus(0);
        plan.setStatus(ProblemImproveEnum.DRAFT);
        if (save(plan)) {
            LmsFrameProblemImproveVO vo = new LmsFrameProblemImproveVO();
            vo.setTempStatus(plan.getTempStatus());
            vo.setId(plan.getId());
            return vo;
        }
        return null;
    }

    @Override
    public LmsFrameProblemImproveAttachment uploadFile(MultipartFile file, LmsFrameProblemImproveVO lmsFrameProblemImproveVO) {
        Long companyId = LoginHelper.getAccount().getCompanyId();
        String folderPath = "frame/ProblemImprove/" + companyId + "/";
        return lmsFrameProblemImproveAttachmentService.saveAndUpload(file, "lims", folderPath, lmsFrameProblemImproveVO.getId(), FrameFileTypeEnum.CHECK_PLAN.getDisplay());
    }

    @Override
    public void downloadFile(Long id, HttpServletResponse response) {
        LmsFrameProblemImproveAttachment attachment = lmsFrameProblemImproveAttachmentService.getById(id);
        String fileUrl = attachment.getObjectKey();
        String orgFileName = attachment.getFileName().replaceAll("\\s*", "");
        lmsFrameProblemImproveAttachmentService.downloadFile(response, "lims", fileUrl, orgFileName);
    }

    @Override
    public boolean deleteFile(Long id) {
        return lmsFrameProblemImproveAttachmentService.deleteBatch(new Long[]{id});
    }

    @Override
    public List<FlowProcess> submitCheckFlow(Long[] ids, Account account) {
        if (org.apache.commons.lang3.ArrayUtils.isEmpty(ids)) {
            return null;
        }

        List<LmsFrameProblemImprove> problemImproveList = super.list(Wrappers.<LmsFrameProblemImprove>query().in("id", ids));
        List<FlowInfo> flowInfoList = new ArrayList<>();

        List<LmsFrameProblemImproveRecord> recordList = Lists.newArrayList();

        List<LmsFrameProblemImprove> updateproblemImproveList = problemImproveList.
                stream().filter(problemImprove -> null != problemImprove).map(problemImprove -> {
            flowInfoList.add(
                    FlowInfo.convertFlowInfo(FlowType.PROBLEM_IMPROVE,
                            account, problemImprove.getId(), problemImprove.getRemark())
            );
            // 设置状态为待审批
            LmsFrameProblemImprove improve1 = new LmsFrameProblemImprove();
            improve1.setId(problemImprove.getId());
            improve1.setStatus(ProblemImproveEnum.EXAMINE);

            LmsFrameProblemImproveRecord record = new LmsFrameProblemImproveRecord();
            record.setProblemImproveId(problemImprove.getId());
            record.setOperator(account.getUserName());
            record.setLiable(account.getUserName());
            record.setRemark("改进/纠正/预防措施管理提交审批");
            record.setType(0);
            record.setTarget(ProblemImproveEnum.EXAMINE.getDisplay());
            record.setOrigin(ProblemImproveEnum.DRAFT.getDisplay());
            recordList.add(record);
            return improve1;

        }).collect(Collectors.toList());
        updateBatchById(updateproblemImproveList);
        if (org.apache.commons.collections.CollectionUtils.isNotEmpty(recordList)) {
            lmsFrameProblemImproveRecordService.saveBatch(recordList);
        }
        return flowProcessClient.saveTask(flowInfoList,account);
    }

    @Override
    public boolean approveFlow(String taskId, String status, String reason) {
        FlowVariables flowVariables = new FlowVariables(taskId);
        FlowInfo flowInfo;
        Map<String, Object> map = new HashMap<>(2);
        Account account = LoginHelper.getAccount();
        RestAssert.fail(org.apache.commons.lang3.StringUtils.isBlank(status), "status不能为空");
        RestAssert.fail(!(status.equalsIgnoreCase("pass") || status.equalsIgnoreCase("back")), "通过状态为'pass'，驳回状态为'back'");
        //获取管理计划id
        LmsFrameProblemImprove improve = new LmsFrameProblemImprove();
//        plan.setAuditId(LoginHelper.getAccount().getUserId());
//        plan.setAuditName(LoginHelper.getAccount().getUserName());
//        plan.setAuditTime(new Date());
//        plan.setApprovalOpinion(reason);

        LmsFrameProblemImproveRecord record = new LmsFrameProblemImproveRecord();
        record.setOperator(account.getUserName());
        record.setLiable(account.getUserName());
        record.setOrigin(ProblemImproveEnum.EXAMINE.getDisplay());
        if ("pass".equals(status)) {
            //管理评审审批通过
            map.put("problemImprovePass", true);
            improve.setStatus(ProblemImproveEnum.EXAMINE_PASS);
            record.setTarget(ProblemImproveEnum.EXAMINE_PASS.getDisplay());
            record.setRemark("改进/纠正/预防措施管理评审通过" + reason);
            record.setType(0);

        } else if ("back".equals(status)) {
            //管理评审驳回
            map.put("problemImprovePass", false);
            improve.setStatus(ProblemImproveEnum.DRAFT);
            record.setTarget(ProblemImproveEnum.EXAMINE_BACK.getDisplay());
            record.setRemark("改进/纠正/预防措施管理评审驳回" + reason);
            record.setType(1);
        }
        map.put(FlowInfo.APPLY_ID, account.getUserId());
        flowVariables.setVariables(map);
        flowInfo = flowProcessClient.complete(flowVariables);
        RestAssert.fail(null == flowInfo, "流程审批错误");
        improve.setId(flowInfo.getId());
        updateById(improve);
        record.setProblemImproveId(flowInfo.getId());
        lmsFrameProblemImproveRecordService.save(record);
        return true;
    }

    @Override
    public LmsFrameProblemImproveVO getVOById(Long id) {
        LmsFrameProblemImprove lmsFrameProblemImprove = getById(id);
        if (null == lmsFrameProblemImprove) {
            return null;
        }
        LmsFrameProblemImproveVO vo = lmsFrameProblemImprove.convert(LmsFrameProblemImproveVO.class);
        vo.setOperator(sysUserClient.getById(lmsFrameProblemImprove.getUid()).getRealname());
        //获取附件
        LmsFrameProblemImproveAttachment attachment = new LmsFrameProblemImproveAttachment();
        attachment.setProblemImproveId(lmsFrameProblemImprove.getId());
        List<LmsFrameProblemImproveAttachment> list = lmsFrameProblemImproveAttachmentService.list(attachment);
        list.forEach(e -> {
            e.setObjectKey(ossClient.getUrl(e.getObjectKey()).toString());
        });
        vo.setLmsFrameProblemImproveAttachments(list);
        return vo;
    }

    @Override
    public boolean add(LmsFrameProblemImprove lmsFrameProblemImprove) {
        LmsFrameProblemImprove entity = new LmsFrameProblemImprove();
        entity.setTempStatus(0);
        LmsFrameProblemImprove temp = baseMapper.selectOne(Wrappers.query(entity));
        if (null != temp) {
            lmsFrameProblemImprove.setId(temp.getId());
            lmsFrameProblemImprove.setTempStatus(1);
            return updateById(lmsFrameProblemImprove);
        }
        lmsFrameProblemImprove.setTempStatus(1);
        return save(lmsFrameProblemImprove);
    }


}
