package cn.iocoder.yudao.module.pms.service.maintain;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.date.LocalDateTimeUtil;
import cn.iocoder.yudao.framework.common.exception.ErrorCode;
import cn.iocoder.yudao.framework.common.exception.ServiceException;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.util.object.BeanUtils;
import cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils;
import cn.iocoder.yudao.module.bpm.api.task.BpmProcessInstanceApi;
import cn.iocoder.yudao.module.pms.controller.admin.failure.vo.IotFailureReportProcessVO;
import cn.iocoder.yudao.module.pms.controller.admin.maintain.IotMaintainController;
import cn.iocoder.yudao.module.pms.controller.admin.maintain.bom.vo.IotMaintainBomSaveReqVO;
import cn.iocoder.yudao.module.pms.controller.admin.maintain.vo.IotMaintainPageReqVO;
import cn.iocoder.yudao.module.pms.controller.admin.maintain.vo.IotMaintainSaveReqVO;
import cn.iocoder.yudao.module.pms.controller.admin.maintain.vo.IotMaintainSaveVO;
import cn.iocoder.yudao.module.pms.controller.admin.stat.vo.OrderVo;
import cn.iocoder.yudao.module.pms.controller.admin.stat.vo.ReportCost;
import cn.iocoder.yudao.module.pms.dal.dataobject.IotDeviceDO;
import cn.iocoder.yudao.module.pms.dal.dataobject.IotProductClassifyDO;
import cn.iocoder.yudao.module.pms.dal.dataobject.failure.IotFailureReportDO;
import cn.iocoder.yudao.module.pms.dal.dataobject.information.IotInformationDbDO;
import cn.iocoder.yudao.module.pms.dal.dataobject.iotlockstock.IotLockStockDO;
import cn.iocoder.yudao.module.pms.dal.dataobject.iotoutbound.IotOutboundDO;
import cn.iocoder.yudao.module.pms.dal.dataobject.maintain.IotMaintainBomDO;
import cn.iocoder.yudao.module.pms.dal.dataobject.maintain.IotMaintainDO;
import cn.iocoder.yudao.module.pms.dal.dataobject.maintain.IotMaintainMaterialsDO;
import cn.iocoder.yudao.module.pms.dal.dataobject.oa.IotOaPersonDO;
import cn.iocoder.yudao.module.pms.dal.mysql.failure.IotFailureReportMapper;
import cn.iocoder.yudao.module.pms.dal.mysql.information.IotInformationDbMapper;
import cn.iocoder.yudao.module.pms.dal.mysql.iotlockstock.IotLockStockMapper;
import cn.iocoder.yudao.module.pms.dal.mysql.iotoutbound.IotOutboundMapper;
import cn.iocoder.yudao.module.pms.dal.mysql.maintain.IotMaintainBomMapper;
import cn.iocoder.yudao.module.pms.dal.mysql.maintain.IotMaintainMapper;
import cn.iocoder.yudao.module.pms.dal.mysql.maintain.IotMaintainMaterialsMapper;
import cn.iocoder.yudao.module.pms.dal.mysql.maintain.material.IotMaintainMaterialMapper;
import cn.iocoder.yudao.module.pms.dal.mysql.oa.IotOaPersonMapper;
import cn.iocoder.yudao.module.pms.enums.common.FailureAuditStatusEnum;
import cn.iocoder.yudao.module.pms.oa.CallBackOaVo;
import cn.iocoder.yudao.module.pms.oa.OaFlow;
import cn.iocoder.yudao.module.pms.service.IotDeviceService;
import cn.iocoder.yudao.module.pms.service.IotProductClassifyService;
import cn.iocoder.yudao.module.system.api.dept.DeptApi;
import cn.iocoder.yudao.module.system.api.dept.dto.DeptRespDTO;
import cn.iocoder.yudao.module.system.api.dingtalk.DingtalkSendApi;
import cn.iocoder.yudao.module.system.api.notify.NotifyMessageSendApi;
import cn.iocoder.yudao.module.system.api.notify.dto.NotifySendSingleToUserReqDTO;
import cn.iocoder.yudao.module.system.api.user.AdminUserApi;
import cn.iocoder.yudao.module.system.api.user.dto.AdminUserRespDTO;
import cn.iocoder.yudao.module.system.service.dept.DeptService;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.google.common.collect.ImmutableMap;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.validation.annotation.Validated;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.*;
import java.util.concurrent.CompletableFuture;
import java.util.stream.Collectors;

import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
import static cn.iocoder.yudao.module.pms.enums.ErrorCodeConstant.IOT_MAINTAIN_BOMS_NOT_EXISTS;
import static cn.iocoder.yudao.module.pms.enums.ErrorCodeConstant.IOT_MAINTAIN_NOT_EXISTS;

/**
 * 维修工单 Service 实现类
 *
 * @author phli
 */
@Service
@Validated
public class IotMaintainServiceImpl implements IotMaintainService {
    public static final String PROCESS_KEY = "maintain-out";
    @Resource
    private IotMaintainMapper iotMaintainMapper;
    @Resource
    private IotMaintainMaterialMapper iotMaintainMaterialMapper;
    @Resource
    private IotLockStockMapper iotLockStockMapper;
    @Resource
    private IotOutboundMapper iotOutboundMapper;
    @Autowired
    private IotFailureReportMapper iotFailureReportMapper;
    @Resource
    private DeptApi deptApi;
    @Resource
    private AdminUserApi adminUserApi;
    @Resource
    private DingtalkSendApi dingtalkSendApi;
    @Resource
    private NotifyMessageSendApi notifyMessageSendApi;
    @Resource
    private BpmProcessInstanceApi processInstanceApi;
    @Autowired
    private IotMaintainBomMapper iotMaintainBomMapper;
    @Autowired
    private IotMaintainMaterialsMapper iotMaintainMaterialsMapper;
    @Autowired
    private IotDeviceService iotDeviceService;
    @Autowired
    private IotProductClassifyService iotProductClassifyService;
    @Autowired
    private IotInformationDbMapper iotInformationDbMapper;
    @Resource
    private DeptService deptService;
    @Autowired
    private IotOaPersonMapper iotOaPersonMapper;
    @Autowired
    private OaFlow oaFlow;

    @Override
    public void approvalMaintain(Long businessKey, Integer bpmStatus) {
        //通过
        IotMaintainDO maintainDO = iotMaintainMapper.selectById(businessKey);
        if (bpmStatus ==2 ){
            maintainDO.setAuditStatus(FailureAuditStatusEnum.APPROVE.getStatus());
            iotMaintainMapper.updateById(maintainDO);
        } else if (bpmStatus ==3 ){
            //不通过
            maintainDO.setAuditStatus(FailureAuditStatusEnum.REJECT.getStatus());
            iotMaintainMapper.updateById(maintainDO);
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public Long submitForApproval(Long id) {
        // 发起BPM流程
        // 获取当前登录人信息
        return 0L;
    }

    @Override
    public Long updateMaintainProcess(IotFailureReportProcessVO iotFailureReportProcessVO) {
        //更新责任人
        IotMaintainDO iotMaintainDO = iotMaintainMapper.selectById(iotFailureReportProcessVO.getId());
        iotMaintainDO.setMaintainPerson(iotFailureReportProcessVO.getAssigneeUserId());
        if (Objects.isNull(iotFailureReportProcessVO.getAssigneeUserId())) throw new ServiceException(new ErrorCode(11,"责任人id不存在"));
        AdminUserRespDTO user = adminUserApi.getUser(iotFailureReportProcessVO.getAssigneeUserId());
        if (Objects.isNull(user)) throw new ServiceException(new ErrorCode(22,"责任人不存在"));
        iotMaintainDO.setMaintainPersonName(user.getNickname());
        iotMaintainMapper.updateById(iotMaintainDO);
        return iotMaintainDO.getId();
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public Long createIotMaintain(IotMaintainSaveVO createReqVO) {
        // 插入工单
        IotMaintainDO iotMaintain = BeanUtils.toBean(createReqVO.getMaintain(), IotMaintainDO.class);
        iotMaintain.setFailureCode("GZ"+ DateUtil.format(new Date(), "yyyyMMddHHmmss"));
        iotMaintain.setFailureName(createReqVO.getMaintain().getDeviceCode()+createReqVO.getMaintain().getDeviceName()+DateUtil.format(new Date(), "yyyyMMddHHmmss"));
        if ("out".equals(iotMaintain.getType())){
            iotMaintain.setStatus("oa");
        } else {
            iotMaintain.setStatus("finished");
        }
        iotMaintain.setDeleted(false);
        iotMaintain.setMaintainPerson(SecurityFrameworkUtils.getLoginUserId());
        if (Objects.isNull(SecurityFrameworkUtils.getLoginUserId())) throw new ServiceException(new ErrorCode(11,"责任人id不存在"));
        AdminUserRespDTO user = adminUserApi.getUser(SecurityFrameworkUtils.getLoginUserId());
        if (Objects.isNull(user)) throw new ServiceException(new ErrorCode(22,"责任人不存在"));
        iotMaintain.setMaintainPersonName(user.getNickname());
        iotMaintain.setMaintainType("手动新增");
        iotMaintain.setExecuteDate(LocalDateTime.now());
        iotMaintain.setPic(JSON.toJSONString(createReqVO.getMaintain().getPics()));
        iotMaintain.setOutFile(JSON.toJSONString(createReqVO.getMaintain().getOutFiles()));
        iotMaintainMapper.insert(iotMaintain);
        //插入工单bom
        List<IotMaintainBomSaveReqVO> maintainMaterials = createReqVO.getMaintainMaterials();
        //内部维修且没有bom的话就抛出异常
        if ("in".equals(createReqVO.getMaintain().getType())&&CollUtil.isEmpty(maintainMaterials)) {
            throw new ServiceException(IOT_MAINTAIN_BOMS_NOT_EXISTS);
        }
        //插入工单物料
        for (IotMaintainBomSaveReqVO maintainMaterial : maintainMaterials) {
            IotMaintainBomDO iotMaintainBomDO = new IotMaintainBomDO();
            iotMaintainBomDO.setBomNodeId(maintainMaterial.getBomNodeId());
            iotMaintainBomDO.setMaintainId(iotMaintain.getId());
            iotMaintainBomDO.setName(maintainMaterial.getName());
            iotMaintainBomDO.setDeleted(false);
            iotMaintainBomMapper.insert(iotMaintainBomDO);
            List<IotMaintainMaterialsDO> iotMaintainMaterialsDOS = new ArrayList<>();
            if (Objects.nonNull(maintainMaterial.getMaterials())) {
                maintainMaterial.getMaterials().forEach(e ->{
                    IotMaintainMaterialsDO iotMaintainMaterialsDO = new IotMaintainMaterialsDO();
                    BeanUtils.copyProperties(e, iotMaintainMaterialsDO);
                    iotMaintainMaterialsDO.setId(null);
                    iotMaintainMaterialsDO.setDeleted(false);
                    iotMaintainMaterialsDO.setMaintainId(iotMaintain.getId());
                    iotMaintainMaterialsDO.setBomId(iotMaintainBomDO.getId());
                    iotMaintainMaterialsDOS.add(iotMaintainMaterialsDO);
                });
                iotMaintainMaterialsMapper.insertBatch(iotMaintainMaterialsDOS);
            }
        }

        //本地库存减少且记录出库
        localStockAndOut(createReqVO, iotMaintain.getId());
//        if ("in".equals(createReqVO.getMaintain().getType())) {
//            String msg = "【PMS】维修工单 - "+createReqVO.getMaintain().getFailureName()+"已处理。"+"["+new Date()+"]";
//            sendMessage(BeanUtils.toBean(iotMaintain, IotMaintainDO.class), "maintain-report", msg);
//        }
        //如果委外发起流程
        if ("out".equals(createReqVO.getMaintain().getType())){
            try {
                oaFlow.createOutRepairFlow(iotMaintain);
            } catch (Exception e) {
                throw new ServiceException(122, e.getMessage());
            }
        }
        //异步写入故障知识库
        CompletableFuture.runAsync(()->{
            IotDeviceDO iotDevice = iotDeviceService.getIotDevice(iotMaintain.getDeviceId());
            if (Objects.nonNull(iotDevice)) {
                IotProductClassifyDO iotProductClassify = iotProductClassifyService.getIotProductClassify(iotDevice.getAssetClass());
                IotInformationDbDO informationDbDO = new IotInformationDbDO();
                informationDbDO.setDeleted(false);
                informationDbDO.setDeviceType(iotDevice.getAssetClass());
                informationDbDO.setClassName(Objects.isNull(iotProductClassify)?"":iotProductClassify.getName());
                informationDbDO.setFailureInfluence(iotMaintain.getFailureInfluence());
                informationDbDO.setFailureSystem(iotMaintain.getFailureSystem());
                informationDbDO.setSolutions(iotMaintain.getSolution());
                informationDbDO.setDescription(iotMaintain.getDescription());
                informationDbDO.setRemark(iotMaintain.getRemark());
                informationDbDO.setDeptId(iotMaintain.getDeptId());
                iotInformationDbMapper.insert(informationDbDO);
            }
        });

        return iotMaintain.getId();
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void updateIotMaintain(IotMaintainSaveVO updateReqVO) {
        // 校验存在
        validateIotMaintainExists(updateReqVO.getMaintain().getId());
        // 更新
        IotMaintainDO updateObj = BeanUtils.toBean(updateReqVO.getMaintain(), IotMaintainDO.class);
        //if ("out".equals(updateObj.getType())&&updateObj.getAuditStatus()==20){
            updateObj.setStatus("finished");
        //}
        updateObj.setPic(JSON.toJSONString(updateReqVO.getMaintain().getPics()));
        if (Objects.nonNull(updateReqVO.getMaintain().getOutFiles())&&CollUtil.isNotEmpty(updateReqVO.getMaintain().getOutFiles())) {
            updateObj.setOutFile(JSON.toJSONString(updateReqVO.getMaintain().getOutFiles()));
        }
        if ("out".equals(updateObj.getType())) {
            updateObj.setStatus("oa");
        }
        updateObj.setExecuteDate(LocalDateTime.now());
        iotMaintainMapper.updateById(updateObj);
        //删除工单bom及物料
        iotMaintainBomMapper.delete("maintain_id", String.valueOf(updateObj.getId()));
        iotMaintainMaterialsMapper.delete("maintain_id", String.valueOf(updateObj.getId()));
        //插入工单bom
        List<IotMaintainBomSaveReqVO> maintainMaterials = updateReqVO.getMaintainMaterials();
        if ("in".equals(updateReqVO.getMaintain().getType())&&CollUtil.isEmpty(maintainMaterials)) {
            throw new ServiceException(IOT_MAINTAIN_NOT_EXISTS);
        }
        //插入工单物料
        for (IotMaintainBomSaveReqVO maintainMaterial : maintainMaterials) {
            IotMaintainBomDO iotMaintainBomDO = new IotMaintainBomDO();
            iotMaintainBomDO.setBomNodeId(maintainMaterial.getBomNodeId());
            iotMaintainBomDO.setMaintainId(updateObj.getId());
            iotMaintainBomDO.setName(maintainMaterial.getName());
            iotMaintainBomDO.setDeleted(false);
            iotMaintainBomMapper.insert(iotMaintainBomDO);
            List<IotMaintainMaterialsDO> iotMaintainMaterialsDOS = new ArrayList<>();
            if (Objects.nonNull(maintainMaterial.getMaterials())) {
                maintainMaterial.getMaterials().forEach(e ->{
                    IotMaintainMaterialsDO iotMaintainMaterialsDO = new IotMaintainMaterialsDO();
                    BeanUtils.copyProperties(e, iotMaintainMaterialsDO);
                    iotMaintainMaterialsDO.setId(null);
                    iotMaintainMaterialsDO.setDeleted(false);
                    iotMaintainMaterialsDO.setMaintainId(updateObj.getId());
                    iotMaintainMaterialsDO.setBomId(iotMaintainBomDO.getId());
                    iotMaintainMaterialsDOS.add(iotMaintainMaterialsDO);
                });
                iotMaintainMaterialsMapper.insertBatch(iotMaintainMaterialsDOS);
            }
        }

        //本地库存减少且记录出库
        localStockAndOut(updateReqVO, updateObj.getId());
        if ("in".equals(updateReqVO.getMaintain().getType())) {
            String msg = "【PMS】维修工单 - "+updateReqVO.getMaintain().getFailureName()+"已处理。"+"["+new Date()+"]";
//            sendMessage(BeanUtils.toBean(updateReqVO.getMaintain(), IotMaintainDO.class), "maintain-report", msg);
        }
        if ("out".equals(updateReqVO.getMaintain().getType())){
            try {
//                IotMaintainDO iotMaintain = BeanUtils.toBean(updateReqVO.getMaintain(), IotMaintainDO.class);
                oaFlow.createOutRepairFlow(updateObj);
            } catch (Exception e) {
                throw new ServiceException(122, e.getMessage());
            }
        }
        //委外发起流程
//        if ("out".equals(updateReqVO.getMaintain().getType())){
//            submitForApproval(updateReqVO.getMaintain().getId());
//            String msg = "【PMS】有新的委外维修流程， 请前往系统审批";
////            sendMessage(BeanUtils.toBean(updateReqVO, IotMaintainDO.class), "maintain-out", msg);
//        }
        //故障上报处理转为工单已完成-orderfinished
        if (StringUtils.isNotBlank(updateReqVO.getMaintain().getFailureId())){
            IotFailureReportDO iotFailureReportDO = iotFailureReportMapper.selectById(updateReqVO.getMaintain().getFailureId());
            iotFailureReportDO.setStatus("orderfinished");
            iotFailureReportMapper.updateById(iotFailureReportDO);
        }
    }

    /**
     * 减少本地库存并记录出库
     * @param maintainSaveVO 维修工单信息
     */
    private void localStockAndOut(IotMaintainSaveVO maintainSaveVO, Long id) {
        List<IotMaintainBomSaveReqVO> maintainMaterials = maintainSaveVO.getMaintainMaterials();
        //判断物料不为空
        if (CollUtil.isNotEmpty(maintainMaterials)) {
            maintainMaterials.stream().filter(g ->Objects.nonNull(g.getMaterials())).forEach(f -> f.getMaterials().forEach(e ->{
                String code = e.getMaterialCode();
                //减去本地库存
                if ("本地库存".equals(e.getMaterialSource())){
                    List<IotLockStockDO> stockDOS = iotLockStockMapper.selectByMap(ImmutableMap.of("material_code", code, "factory_id", e.getFactoryId(),"cost_center_id", e.getCostCenterId()));
                    if (CollUtil.isNotEmpty(stockDOS)) {
                        IotLockStockDO iotLockStockDO = stockDOS.get(0);
                        BigDecimal quantity = iotLockStockDO.getQuantity();
                        BigDecimal subtract = quantity.subtract(e.getQuantity());
//                            if (subtract.compareTo(BigDecimal.ZERO) < 0){
//                                throw new ServiceException(IOT_LOCK_STOCK_FUSHU);
//                            }
                        iotLockStockDO.setQuantity(subtract);
                        iotLockStockMapper.updateById(iotLockStockDO);
                    }
                }
                //记录出库
                IotOutboundDO outboundDO = new IotOutboundDO();
                outboundDO.setDeptId(maintainSaveVO.getMaintain().getDeptId());
                outboundDO.setMaterialCode(code);
                outboundDO.setMaterialName(e.getMaterialName());
                outboundDO.setDeliveryTime(LocalDateTimeUtil.now());
                outboundDO.setReason("故障维修");
                //将维修工单的id设置到bizId
                outboundDO.setBizId(id);
                outboundDO.setStatus(0);
                outboundDO.setType(1);
                outboundDO.setDeleted(false);
                outboundDO.setUnit(e.getUnit());
                outboundDO.setUnitPrice(e.getUnitPrice());
                outboundDO.setQuantity(e.getQuantity());
                iotOutboundMapper.insert(outboundDO);
            }));
        }
        //更新故障上报的状态为工单处理完成
        IotMaintainSaveReqVO iotMaintain = maintainSaveVO.getMaintain();
        if (Objects.nonNull(iotMaintain.getFailureId())){
            IotFailureReportDO iotFailureReportDO = iotFailureReportMapper.selectById(iotMaintain.getFailureId());
            if (Objects.nonNull(iotFailureReportDO)){
                iotFailureReportDO.setStatus("orderfinished");
                iotFailureReportMapper.updateById(iotFailureReportDO);
            }
        }
    }


    private void sendMessage(IotMaintainDO iotMaintainDO, String templateCode, String msg) {
        Long loginUserDeptId = SecurityFrameworkUtils.getLoginUserDeptId();
        DeptRespDTO dept = deptApi.getDept(loginUserDeptId);
        DeptRespDTO parentDept = deptApi.getDeptNoPermission(dept.getParentId());
        Map<String, Object> templateParams = new HashMap<>();
        templateParams.put("name", iotMaintainDO.getDeviceName());
//        CompletableFuture.runAsync(() ->{
            if (Objects.nonNull(parentDept.getLeaderUserId())){
                notifyMessageSendApi.sendSingleMessageToAdmin(new NotifySendSingleToUserReqDTO()
                        .setUserId(parentDept.getLeaderUserId()).setTemplateCode(templateCode).setTemplateParams(templateParams));
                AdminUserRespDTO user = adminUserApi.getUser(parentDept.getLeaderUserId());
                if (Objects.nonNull(user)) {
                    dingtalkSendApi.send(user.getMobile(), msg,"","","DeepOil-PMS消息提醒");
                }
            }

//        });
    }

    @Override
    public void deleteIotMaintain(Long id) {
        // 校验存在
        validateIotMaintainExists(id);
        // 删除
        iotMaintainMapper.deleteById(id);
    }

    private void validateIotMaintainExists(Long id) {
        if (iotMaintainMapper.selectById(id) == null) {
            throw exception(IOT_MAINTAIN_NOT_EXISTS);
        }
    }

    @Override
    public IotMaintainDO getIotMaintain(Long id) {
        return iotMaintainMapper.selectById(id);
    }

    @Override
    public PageResult<IotMaintainDO> getIotMaintainPage(IotMaintainPageReqVO pageReqVO) {
        Set<Long> ids = new HashSet<>();
        if (Objects.nonNull(pageReqVO.getDeptId())) {
            ids = deptService.getChildDeptIdListFromCache(pageReqVO.getDeptId());
            ids.add(pageReqVO.getDeptId());
        }
        return iotMaintainMapper.selectPage(pageReqVO, ids);
    }

    @Override
    public PageResult<IotMaintainDO> getIotMaintainPageApp(IotMaintainPageReqVO pageReqVO) {
        Set<Long> ids = new HashSet<>();
        if (Objects.nonNull(pageReqVO.getDeptId())) {
            ids = deptService.getChildDeptIdListFromCache(pageReqVO.getDeptId());
            ids.add(pageReqVO.getDeptId());
        }
        return iotMaintainMapper.selectPageApp(pageReqVO, ids);
    }

    @Override
    public void syncWordOrderData(List<Long> deviceIds, Long deptId) {
        List<IotMaintainDO> maintainDOS = iotMaintainMapper.selectByStatusAndAuditStatusAndDeviceId("finished", 20, deviceIds);
        if(!maintainDOS.isEmpty()){
            maintainDOS.forEach(maintainDO -> maintainDO.setDeptId(deptId));
            iotMaintainMapper.updateBatch(maintainDOS);
        }

    }


    @Override
    public PageResult<OrderVo> getNotice(OrderVo pageReqVO) {

        IPage<OrderVo> notices = iotMaintainMapper.selectNotice(Page.of(pageReqVO.getPageNo(), pageReqVO.getPageSize()), pageReqVO);
        return new PageResult<>(notices.getRecords(), notices.getTotal());
    }


    @Override
    public void methodDeal(IotMaintainController.MaintainMethod method) {
        IotMaintainDO iotMaintainDO = iotMaintainMapper.selectById(method.getId());
        iotMaintainDO.setMaintainMethod(method.getMaintainMethod());
        iotMaintainDO.setMethodDescription(method.getMethodDescription());
        iotMaintainDO.setStatus("tx");
        //如果维修方式是基地维修的话设置维修类型为jd维修
        if ("jd".equals(method.getMaintainMethod())) {
            iotMaintainDO.setType("jd");
            AdminUserRespDTO user = adminUserApi.getUser(iotMaintainDO.getMaintainPerson());
            if (Objects.nonNull(user)) {
                //如果基地维修，将该工单的部门id设置为维修人员所在部门id
                iotMaintainDO.setDeptId(user.getDeptId());
            }
        }
        iotMaintainMapper.updateById(iotMaintainDO);
    }

    @Override
    public void oaDeal(CallBackOaVo callBackOaVo) {
        List<IotMaintainDO> iotMaintainDOS = iotMaintainMapper.selectList("request_id", callBackOaVo.getRequestId());
        if (CollUtil.isEmpty(iotMaintainDOS)) {
            throw new ServiceException(new ErrorCode(300,"无该流程"));
        }
        IotMaintainDO iotMaintainDO = iotMaintainDOS.get(0);
        iotMaintainDO.setOaFlowNo(callBackOaVo.getFlowNo());
        if ("0".equals(callBackOaVo.getIfSuccess())){
            iotMaintainDO.setStatus("oareject");
        } else {
            iotMaintainDO.setStatus("finished");
        }
        iotMaintainDO.setSuggestionJson(JSON.toJSONString(callBackOaVo.getMainData()));
//        List<OaVo.MainData> mainData = callBackOaVo.getMainData();
//        mainData.forEach(e -> {
//            if ("wxyy".equals(e.getFieldName())&&!iotMaintainDO.getMaintainDescription().equals(e.getFieldValue())) {
//                iotMaintainDO.setMaintainDescription(e.getFieldValue());
//            } else if ("ygjey".equals(e.getFieldName())&&!iotMaintainDO.getMaintainFee().toString().equals(e.getFieldValue())){
//                iotMaintainDO.setMaintainFee(new BigDecimal(e.getFieldValue()));
//            } else if ("wxdd".equals(e.getFieldName())&&!iotMaintainDO.getAddress().equals(e.getFieldValue())){
//                iotMaintainDO.setAddress(e.getFieldValue());
//            } else if ("ggxh".equals(e.getFieldName())&&!iotMaintainDO.getModel().equals(e.getFieldValue())) {
//                iotMaintainDO.setModel(e.getFieldValue());
//            } else if ("qyrq".equals(e.getFieldName())&&!iotMaintainDO.getEnableDate().equals(e.getFieldValue())) {
//                iotMaintainDO.setEnableDate(e.getFieldValue());
//            } else if ("wxlb".equals(e.getFieldName())&&!iotMaintainDO.getMaintainClassify().equals(e.getFieldValue())) {
//                iotMaintainDO.setMaintainClassify(e.getFieldValue());
//            } else if ("yzglxs".equals(e.getFieldName())&&!iotMaintainDO.getKmHour().equals(e.getFieldValue())) {
//                iotMaintainDO.setKmHour(e.getFieldValue());
//            } else if ("wxcj".equals(e.getFieldName())&&!iotMaintainDO.getSupplier().equals(e.getFieldValue())) {
//                iotMaintainDO.setSupplier(e.getFieldValue());
//            } else if ("gzms".equals(e.getFieldName())&&!iotMaintainDO.getDescription().equals(e.getFieldValue())) {
//                iotMaintainDO.setDescription(e.getFieldValue());
//            } else if ("wxxm".equals(e.getFieldName())&&!iotMaintainDO.getMaintainItem().equals(e.getFieldValue())) {
//                iotMaintainDO.setMaintainItem(e.getFieldValue());
//            }
//        });
        iotMaintainMapper.updateById(iotMaintainDO);
    }

    public List<IotOaPersonDO> getMaintainPerson(String id) {
        Long loginUserId;
        if (StringUtils.isBlank(id)||"undefined".equals(id)) {
            loginUserId = SecurityFrameworkUtils.getLoginUserId();
        } else {
            loginUserId = Long.valueOf(id);
        }
        AdminUserRespDTO user = adminUserApi.getUser(loginUserId);
        if (Objects.isNull(user)) {
            throw new ServiceException(new ErrorCode(666,"用户不存在"));
        }
        List<IotOaPersonDO> currentUser;
        if ("admin".equals(user.getUsername())) {
            currentUser = iotOaPersonMapper.selectList().stream().filter(e -> "0".equals(e.getStatus()) || "1".equals(e.getStatus()) || "2".equals(e.getStatus()) || "3".equals(e.getStatus())).collect(Collectors.toList());
            return currentUser;
        } else {
            String workcode = user.getUsername();
            currentUser = iotOaPersonMapper.selectList("workcode", workcode);
        }
        if (CollUtil.isNotEmpty(currentUser)) {
            return currentUser;
        }
        Long deptId = user.getDeptId();
        DeptRespDTO dept = deptApi.getDeptNoPermission(deptId);
        String name = dept.getName();
        String companyCode = "";
        if (name.contains("瑞恒")) {
            companyCode = "6000";
        } else if (name.contains("瑞都")) {
            companyCode = "5020";
        } else if (name.contains("瑞鹰")) {
            companyCode = "6010";
        } else {
            DeptRespDTO dept1 = deptApi.getDeptNoPermission(dept.getParentId());
            String name1 = dept1.getName();
            if (name1.contains("瑞恒")) {
                companyCode = "6000";
            } else if (name1.contains("瑞都")) {
                companyCode = "5020";
            } else if (name1.contains("瑞鹰")) {
                companyCode = "6010";
            } else {
                DeptRespDTO dept2 = deptApi.getDeptNoPermission(dept1.getParentId());
                String name2 = dept2.getName();
                if (name2.contains("瑞恒")) {
                    companyCode = "6000";
                } else if (name2.contains("瑞都")) {
                    companyCode = "5020";
                } else if (name2.contains("瑞鹰")) {
                    companyCode = "6010";
                } else {
                    DeptRespDTO dept3= deptApi.getDeptNoPermission(dept2.getParentId());
                    String name3 = dept3.getName();
                    if (name3.contains("瑞恒")) {
                        companyCode = "6000";
                    } else if (name3.contains("瑞都")) {
                        companyCode = "5020";
                    } else if (name3.contains("瑞鹰")) {
                        companyCode = "6010";
                    }
                }
            }
        }
        List<IotOaPersonDO> companyUsers = iotOaPersonMapper.selectList("subcompanycode", companyCode);
        List<IotOaPersonDO> result = companyUsers.stream().filter(e -> "0".equals(e.getStatus()) || "1".equals(e.getStatus()) || "2".equals(e.getStatus()) || "3".equals(e.getStatus())).collect(Collectors.toList());
        return result;
    }

    public List<IotOaPersonDO> getProjectPerson(String id) {
        Long loginUserId;
        if (StringUtils.isBlank(id)||"undefined".equals(id)) {
            loginUserId = SecurityFrameworkUtils.getLoginUserId();
        } else {
            loginUserId = Long.valueOf(id);
        }
        AdminUserRespDTO user = adminUserApi.getUser(loginUserId);
        if (Objects.isNull(user)) {
            throw new ServiceException(new ErrorCode(666,"用户不存在"));
        }
        List<IotOaPersonDO> currentUser = Collections.emptyList();
        if ("admin".equals(user.getUsername())) {
            currentUser = iotOaPersonMapper.selectList().stream().filter(e -> "0".equals(e.getStatus()) || "1".equals(e.getStatus()) || "2".equals(e.getStatus()) || "3".equals(e.getStatus())).collect(Collectors.toList());
            return currentUser;
        }
        if (CollUtil.isNotEmpty(currentUser)) {
            return currentUser;
        }
        Long deptId = user.getDeptId();
        DeptRespDTO dept = deptApi.getDeptNoPermission(deptId);
        String name = dept.getName();
        String companyCode = "";
        if (name.contains("瑞恒")) {
            companyCode = "6000";
        } else if (name.contains("瑞都")) {
            companyCode = "5020";
        } else if (name.contains("瑞鹰")) {
            companyCode = "6010";
        } else {
            Long parentId = dept.getParentId();
            DeptRespDTO dept1 = deptApi.getDeptNoPermission(parentId);
            String name1 = dept1.getName();
            if (name1.contains("瑞恒")) {
                companyCode = "6000";
            } else if (name1.contains("瑞都")) {
                companyCode = "5020";
            } else if (name1.contains("瑞鹰")) {
                companyCode = "6010";
            } else {
                DeptRespDTO dept2 = deptApi.getDeptNoPermission(dept1.getParentId());
                String name2 = dept2.getName();
                if (name2.contains("瑞恒")) {
                    companyCode = "6000";
                } else if (name2.contains("瑞都")) {
                    companyCode = "5020";
                } else if (name2.contains("瑞鹰")) {
                    companyCode = "6010";
                } else {
                    DeptRespDTO dept3= deptApi.getDeptNoPermission(dept2.getParentId());
                    String name3 = dept3.getName();
                    if (name3.contains("瑞恒")) {
                        companyCode = "6000";
                    } else if (name3.contains("瑞都")) {
                        companyCode = "5020";
                    } else if (name3.contains("瑞鹰")) {
                        companyCode = "6010";
                    }
                }
            }
        }
        List<IotOaPersonDO> companyUsers = iotOaPersonMapper.selectList("subcompanycode", companyCode);
        List<IotOaPersonDO> result = companyUsers.stream().filter(e -> "0".equals(e.getStatus()) || "1".equals(e.getStatus()) || "2".equals(e.getStatus()) || "3".equals(e.getStatus())).collect(Collectors.toList());
        return result;
    }


    @Override
    public Boolean ifFinished(List<Long> deviceIds) {
        List<IotMaintainDO> maintains = iotMaintainMapper.selectByStatusAndAuditStatusAndDeviceId(null, null, deviceIds);
        boolean todo = maintains.stream().anyMatch(e -> !"finished".equals(e.getStatus()));
        return !todo;
    }

    @Override
    public PageResult<ReportCost> getReportCost(IotMaintainPageReqVO pageReqVO) {
        IPage<ReportCost> page = iotMaintainMapper.getCost(
                new Page<>(pageReqVO.getPageNo(), pageReqVO.getPageSize()), pageReqVO);
        if (CollUtil.isNotEmpty(page.getRecords())) {
            return new PageResult<>(page.getRecords(), page.getTotal());
        }

        return new PageResult<>(page.getRecords(), page.getTotal());
    }
}
