package cn.estsh.i3plus.ext.mes.pcn.apiservice.serviceimpl.busi.step.bu;

import cn.estsh.i3plus.ext.mes.pcn.api.base.ISxPcnHttpService;
import cn.estsh.i3plus.ext.mes.pcn.api.base.ISxWorkOrderExtService;
import cn.estsh.i3plus.ext.mes.pcn.api.base.IWorkCenterExtService;
import cn.estsh.i3plus.ext.mes.pcn.api.busi.IPackageExtService;
import cn.estsh.i3plus.ext.mes.pcn.api.busi.IProduceSnExtService;
import cn.estsh.i3plus.ext.mes.pcn.api.busi.bu.IOuterPackageSnService;
import cn.estsh.i3plus.ext.mes.pcn.pojo.bean.*;
import cn.estsh.i3plus.ext.mes.pcn.pojo.repository.*;
import cn.estsh.i3plus.ext.mes.pcn.pojo.util.ConvertBeanExt;
import cn.estsh.i3plus.ext.mes.pcn.pojo.util.MesPcnExtConstWords;
import cn.estsh.i3plus.ext.mes.pcn.pojo.util.MesPcnExtEnumUtil;
import cn.estsh.i3plus.mes.pcn.serviceimpl.base.BaseStepService;
import cn.estsh.i3plus.mes.pcn.util.LocaleUtil;
import cn.estsh.i3plus.mes.pcn.util.PcnHttpUtil;
import cn.estsh.i3plus.platform.common.convert.ConvertBean;
import cn.estsh.i3plus.platform.common.exception.ImppExceptionEnum;
import cn.estsh.i3plus.platform.common.tool.JsonUtilTool;
import cn.estsh.i3plus.platform.common.tool.MathOperation;
import cn.estsh.i3plus.pojo.base.bean.BaseResultBean;
import cn.estsh.i3plus.pojo.base.enumutil.CommonEnumUtil;
import cn.estsh.i3plus.pojo.base.enumutil.MesPcnEnumUtil;
import cn.estsh.i3plus.pojo.mes.bean.MesPackageDetail;
import cn.estsh.i3plus.pojo.mes.model.StationRequestBean;
import cn.estsh.i3plus.pojo.mes.model.StationResultBean;
import cn.estsh.i3plus.pojo.mes.model.StepResult;
import cn.estsh.impp.framework.boot.exception.ImppExceptionBuilder;
import com.alibaba.fastjson.JSONObject;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * 工步业务----新返工工位-返工流程-大包装解绑工步
 * @USER: steven.peng
 * @DATE: 2023-01-11 10:20
 * */
@Slf4j
@Service("sxOuterPackageSnUnBindStepService")
public class SxOuterPackageSnUnBindStepService extends BaseStepService {

    @Autowired
    private IProduceSnExtService produceSnExtService;

    @Autowired
    private ISxWorkOrderExtService workOrderExtService;

    @Autowired
    private IPackageExtService packageExtService;

    @Autowired
    private IOuterPackageSnService iOuterPackageSnService;

    @Autowired
    private MesOuterPackageRepository mesOuterPackageRepository;

    @Autowired
    private MesOuterPackageDetailRepository mesOuterPackageDetailRepository;

    @Autowired
    private MesProduceSnExtRepository produceSnExtRepository;

    @Autowired
    private MesProduceSnRepairRepository produceSnRepairRepository;

    @Autowired
    private MesPackageExtRepository packageExtRepository;

    @Autowired
    private IPackageExtService iPackageExtService;

    @Autowired
    private IWorkCenterExtService workCenterExtService;

    @Autowired
    private ISxPcnHttpService pcnHttpService;

    @Override
    public StepResult execute(StationRequestBean reqBean) {
        log.info("sxOuterPackageSnUnBindStepService[execute] 参数：{}", reqBean);

        StationResultBean resultBean = new StationResultBean();
        String err;
        if (StringUtils.isEmpty(reqBean.getOrganizeCode())) {
            err = LocaleUtil.transferLanguage(reqBean.getUserInfo(), "入参缺少工厂代码");
            this.sendMessage(reqBean, resultBean, err, MesPcnEnumUtil.STATION_BUSI_TYPE.MESSAGE, MesPcnEnumUtil.STATION_DATA_TYPE.EXP_TEXT);
            return StepResult.getNonComplete(err);
        }

        if (StringUtils.isEmpty(reqBean.getWorkOrderNo())) {
            err = LocaleUtil.transferLanguage(reqBean.getUserInfo(), "入参缺少工单号");
            this.sendMessage(reqBean, resultBean, err, MesPcnEnumUtil.STATION_BUSI_TYPE.MESSAGE, MesPcnEnumUtil.STATION_DATA_TYPE.EXP_TEXT);
            return StepResult.getNonComplete(err);
        }

        if (StringUtils.isEmpty(reqBean.getScanInfo())) {
            err = LocaleUtil.transferLanguage(reqBean.getUserInfo(), "入参缺少扫描的条码信息");
            this.sendMessage(reqBean, resultBean, err, MesPcnEnumUtil.STATION_BUSI_TYPE.MESSAGE, MesPcnEnumUtil.STATION_DATA_TYPE.EXP_TEXT);
            return StepResult.getNonComplete(err);
        }
        // 获取当前工单，并判断当前工单类型
        MesWorkOrderExt workOrderExt = workOrderExtService.getWorkOrderExtByOrderNo(reqBean.getOrganizeCode(), reqBean.getWorkOrderNo());
        if (null == workOrderExt) {
            err = String.format(LocaleUtil.transferLanguage(reqBean.getUserInfo(), "工单[%s]无效,不能操作"), reqBean.getWorkOrderNo());
            sendMessage(reqBean, resultBean, err, MesPcnEnumUtil.STATION_BUSI_TYPE.MESSAGE, MesPcnEnumUtil.STATION_DATA_TYPE.EXP_TEXT);
            return StepResult.getNonComplete(err);
        }
        if (MathOperation.compareTo(workOrderExt.getCompleteQty(), workOrderExt.getQty()) >= 0) {
            err = String.format(LocaleUtil.transferLanguage(reqBean.getUserInfo(), "工单[%s]数量已完成,不能操作"), reqBean.getWorkOrderNo());
            sendMessage(reqBean, resultBean, err, MesPcnEnumUtil.STATION_BUSI_TYPE.MESSAGE, MesPcnEnumUtil.STATION_DATA_TYPE.EXP_TEXT);
            return StepResult.getNonComplete(err);
        }
        if (MesPcnExtEnumUtil.WORK_ORDER_STATUS.OPEN.getValue() != workOrderExt.getWorkOrderStatus()) {
            err = String.format(LocaleUtil.transferLanguage(reqBean.getUserInfo(), "工单[%s]状态为[%s],不能操作"),
                    reqBean.getWorkOrderNo(), MesPcnExtEnumUtil.WORK_ORDER_STATUS.valueOfDescription(workOrderExt.getWorkOrderStatus()));
            sendMessage(reqBean, resultBean, err, MesPcnEnumUtil.STATION_BUSI_TYPE.MESSAGE, MesPcnEnumUtil.STATION_DATA_TYPE.EXP_TEXT);
            return StepResult.getNonComplete(err);
        }
        // 通过大包装条码查询大包装条码主表获取记录
        List<MesOuterPackage> mesOuterPackages =  iOuterPackageSnService.getOuterPackageListByPackageNo(reqBean.getOrganizeCode(),reqBean.getScanInfo());
        if(null == mesOuterPackages || mesOuterPackages.size() == 0 ){
            err = String.format(LocaleUtil.transferLanguage(reqBean.getUserInfo(), "大包装条码[%s]查询主表查询不到记录，不能操作"),
                    reqBean.getScanInfo(), MesPcnExtEnumUtil.WORK_ORDER_STATUS.valueOfDescription(workOrderExt.getWorkOrderStatus()));
            sendMessage(reqBean, resultBean, err, MesPcnEnumUtil.STATION_BUSI_TYPE.MESSAGE, MesPcnEnumUtil.STATION_DATA_TYPE.EXP_TEXT);
            return StepResult.getNonComplete(err);
        }

        List<MesOuterPackageDetail> mesOuterPackageDetails =  iOuterPackageSnService.getOuterPackageDetailListByOuterPackageNo(reqBean.getOrganizeCode(),reqBean.getScanInfo());
        if(null == mesOuterPackageDetails || mesOuterPackageDetails.size() == 0 ){
            err = String.format(LocaleUtil.transferLanguage(reqBean.getUserInfo(), "大包装条码[%s]查询明细查询不到记录，不能操作"),
                    reqBean.getScanInfo(), MesPcnExtEnumUtil.WORK_ORDER_STATUS.valueOfDescription(workOrderExt.getWorkOrderStatus()));
            sendMessage(reqBean, resultBean, err, MesPcnEnumUtil.STATION_BUSI_TYPE.MESSAGE, MesPcnEnumUtil.STATION_DATA_TYPE.EXP_TEXT);
            return StepResult.getNonComplete(err);
        }

        if(reqBean.getWorkOrderNo().equals(mesOuterPackages.get(0).getWorkOrderNo())){
            err = String.format(LocaleUtil.transferLanguage(reqBean.getUserInfo(), "此大包装条码[%s]已在工单号[%s]返工过，不能再次返工"),
                    reqBean.getScanInfo(),reqBean.getWorkOrderNo(),MesPcnExtEnumUtil.WORK_ORDER_STATUS.valueOfDescription(workOrderExt.getWorkOrderStatus()));
            sendMessage(reqBean, resultBean, err, MesPcnEnumUtil.STATION_BUSI_TYPE.MESSAGE, MesPcnEnumUtil.STATION_DATA_TYPE.EXP_TEXT);
            return StepResult.getNonComplete(err);
        }

        MesWorkCenterExt workCenterExt = workCenterExtService.getWorkCenterExtByWorkCenterCode(reqBean.getOrganizeCode(), workOrderExt.getWorkCenterCode());
        if (null == workCenterExt) {
            throw ImppExceptionBuilder.newInstance()
                    .setSystemID(CommonEnumUtil.SOFT_TYPE.MES_PCN.getCode())
                    .setErrorCode(ImppExceptionEnum.VARIFY_EXCEPTION.getCode())
                    .setErrorDetail("生产线代码[%s]无效",  workOrderExt.getWorkCenterCode())
                    .build();
        }
        if (StringUtils.isEmpty(workCenterExt.getShiftCode()) || StringUtils.isEmpty(workCenterExt.getWorkTime())) {
            throw ImppExceptionBuilder.newInstance()
                    .setSystemID(CommonEnumUtil.SOFT_TYPE.MES_PCN.getCode())
                    .setErrorCode(ImppExceptionEnum.VARIFY_EXCEPTION.getCode())
                    .setErrorDetail("生产线[%s]未启动班次",  workOrderExt.getWorkCenterCode())
                    .build();
        }

        MesOuterPackage ms = mesOuterPackages.get(0);
        // 将大包装条码状态为未封箱（初始创建状态），大包装主表里面工单号清空，qty改为0
        ms.setQty(new Double(0));
        ms.setShiftCode("");
        ms.setLotNo("");
      //ms.setPartNameRdd("");
      //ms.setPartNo("");
        ms.setWorkTime("");
        ms.setWorkCellName("");
        ms.setWorkCenterCode("");
        ms.setWorkCenterName("");
        ms.setWorkOrderType(0);
        ms.setWorkOrderNo(reqBean.getWorkOrderNo());
     /* ms.setModifyUser(reqBean.getUserInfo());
        ms.setWorkOrderNo(reqBean.getWorkOrderNo());
        ms.setWorkCellCode(reqBean.getWorkCellCode());
        ms.setPartNo();
        ms.setWorkCenterCode(reqBean.getWorkCenterCode());
        ms.setWorkTime(workCenterExt.getWorkTime());
        ms.setShiftCode(workCenterExt.getShiftCode());*/
        ms.setIsSealed(MesPcnExtEnumUtil.PACKAGE_IS_SEALED.UNSEALED.getValue());
        mesOuterPackageRepository.save(ms);
        // 大包装明细表里面状态全改为解绑
        mesOuterPackageDetails.forEach(o -> {
            o.setBindStatus(MesPcnExtEnumUtil.PACKAGE_BIND_STATUS.UNBIND.getValue());
            o.setWorkOrderNo(reqBean.getWorkOrderNo());
            o.setWorkCellCode("");
            o.setWorkCenterCode("");
            o.setWorkCellName("");
            o.setWorkCenterName("");
            o.setModifyUser(reqBean.getUserInfo());
            mesOuterPackageDetailRepository.save(o);
        });

        // 得到小包装条码集合
        List<String> innerPackageNoList = mesOuterPackageDetails.stream().filter(o -> (null != o && !StringUtils.isEmpty(o.getInnerPackageNo()))).map(MesOuterPackageDetail::getInnerPackageNo).collect(Collectors.toList());

        Map<String, List<String>> packageNoByWorkOrderWithMap = new HashMap<>();

        for (int i = 0; i < innerPackageNoList.size(); i++) {
            // 通过小包装条码去包装表中查询得到本体条码（一对一的关系）
            MesPackageDetail mesPackageDetail = iPackageExtService.getPackageDetailByPackNo(reqBean.getOrganizeCode(), innerPackageNoList.get(i));
            if (null == mesPackageDetail || StringUtils.isEmpty(mesPackageDetail.getSerialNumber())) {
                String errInfo = String.format(LocaleUtil.transferLanguage(reqBean.getUserInfo(), "大包装条码[%s]对应的小包装条码[%s]无效"), innerPackageNoList.get(i));
                sendMessage(reqBean, new StationResultBean(), errInfo, MesPcnEnumUtil.STATION_BUSI_TYPE.MESSAGE, MesPcnEnumUtil.STATION_DATA_TYPE.EXP_TEXT);
                return StepResult.getNonComplete(errInfo);
            }

            MesProduceSnExt produceSnExt = produceSnExtService.getProduceSnExtBySn(reqBean.getOrganizeCode(), mesPackageDetail.getSerialNumber());
            if (null == produceSnExt || StringUtils.isEmpty(produceSnExt.getSerialNumber())) {
                String errInfo = String.format(LocaleUtil.transferLanguage(reqBean.getUserInfo(), "大包装条码[%s]对应的小包装条码[%s]查询不到对应的本体条码"), innerPackageNoList.get(i));
                sendMessage(reqBean, new StationResultBean(), errInfo, MesPcnEnumUtil.STATION_BUSI_TYPE.MESSAGE, MesPcnEnumUtil.STATION_DATA_TYPE.EXP_TEXT);
                return StepResult.getNonComplete(errInfo);
            }

            String lastWorkOrder = produceSnExt.getLastWorkOrderNo();

            // 将本体条码与返工工单进行绑定
            MesProduceSnRepair produceSnRepair = new MesProduceSnRepair();
            produceSnRepair.setSerialNumber(produceSnExt.getSerialNumber());
            produceSnRepair.setProductSn(produceSnExt.getSerialNumber());
            produceSnRepair.setPartNo(produceSnExt.getPartNo());
            produceSnRepair.setPartNameRdd(produceSnExt.getPartNameRdd());
            produceSnRepair.setWorkCenterCode(reqBean.getWorkCenterCode());
            produceSnRepair.setWorkCellCode(reqBean.getWorkCellCode());
            produceSnRepair.setWorkOrderNo(reqBean.getWorkOrderNo());
            produceSnRepair.setInitWorkOrderNo(produceSnExt.getLastWorkOrderNo());
            produceSnRepair.setSnType(MesPcnExtEnumUtil.PRODUCE_SN_TYPE.REWORK_SN.getValue());
            produceSnRepair.setOrganizeCode(reqBean.getOrganizeCode());
            ConvertBean.serviceModelInitialize(produceSnRepair, reqBean.getUserInfo());
            produceSnRepair.setSystemSyncStatus(MesPcnExtEnumUtil.IF_SYNC_STATUS.NO_SYNC.getValue());
            produceSnRepairRepository.insert(produceSnRepair);
            // 小包装条码对应的本体条码状态要改为返工
            produceSnExt.setSnStatus(MesPcnExtEnumUtil.PRODUCE_SN_STATUS.REPAIR.getValue());
            produceSnExt.setLastWorkOrderNo(reqBean.getWorkOrderNo());
            produceSnExtService.packSnExtProcess(produceSnExt, reqBean.getOrganizeCode(), reqBean.getWorkCenterCode(), reqBean.getWorkCellCode());
            ConvertBean.serviceModelUpdate(produceSnExt, reqBean.getUserInfo());
            produceSnExt.setSystemSyncStatus(MesPcnExtEnumUtil.IF_SYNC_STATUS.NO_SYNC.getValue());
            new ConvertBeanExt(produceSnExt).convertBean(produceSnExt);
            produceSnExtRepository.save(produceSnExt);

         //   MesPackageDetail packageDetail = packageExtService.getPackageDetailBySn(reqBean.getOrganizeCode(), reqBean.getSerialNumber());
            if (null != mesPackageDetail) {
                MesPackageExt packageExt = packageExtService.getPackageByPackNo(reqBean.getOrganizeCode(), mesPackageDetail.getPackageNo());
                if (null != packageExt) {
                    packageExt.setLastWorkOrderNo(reqBean.getWorkOrderNo());
                    ConvertBean.serviceModelUpdate(packageExt, reqBean.getUserInfo());
                    packageExt.setSystemSyncStatus(MesPcnExtEnumUtil.IF_SYNC_STATUS.NO_SYNC.getValue());
                    new ConvertBeanExt(packageExt).convertBean(packageExt);
                    packageExtRepository.save(packageExt);
                }
                List<String> packNoList = packageNoByWorkOrderWithMap.get(lastWorkOrder);

                if(CollectionUtils.isEmpty(packNoList)) packNoList = new ArrayList<>();
                packNoList.add(mesPackageDetail.getPackageNo());
                packageNoByWorkOrderWithMap.put(lastWorkOrder, packNoList);
            }
        }

        log.error("净水器线 --- 返工条码 --- 修改返工范围数据 --- 返工条码:{},工单号:{},工厂代码:{},用户名:{} ", JSONObject.toJSONString(packageNoByWorkOrderWithMap),
                reqBean.getWorkOrderNo(), reqBean.getOrganizeCode(), reqBean.getUserInfo());

        // 更新返工范围信息
        Map<String, String> params = new HashMap<>();
        params.put(MesPcnExtConstWords.MODEL, JSONObject.toJSONString(packageNoByWorkOrderWithMap));
        params.put(MesPcnExtConstWords.REWORK_ORDER_NO, reqBean.getWorkOrderNo());
        params.put(MesPcnExtConstWords.ORGANIZE_CODE, reqBean.getOrganizeCode());
        params.put(MesPcnExtConstWords.USER_NAME, reqBean.getUserInfo());
        String requestUrl = pcnHttpService.getRequestUrl(reqBean.getOrganizeCode(), MesPcnExtConstWords.UPDATE_REWORK_RANGE_ORDER_NO_URL);
        String data = PcnHttpUtil.doPost(requestUrl, params);
        BaseResultBean baseResultBean = null;
        if (!StringUtils.isEmpty(data)) {
            baseResultBean = JsonUtilTool.decode(data, BaseResultBean.class);
        } else {
            log.error("净水器线 返工条码 修改返工范围数据 HTTP[{}]调用主接口失败", requestUrl);
        }
        if (null == baseResultBean || !baseResultBean.success) {
            log.error("净水器线 返工条码 修改返工范围数据 HTTP[{}]调用主接口失败", requestUrl);
        }

        return StepResult.getSuccessComplete();
    }
}
