package nc.bs.mmpac.pmo.pac0002.bp.rule;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import nc.bs.dao.BaseDAO;
import nc.bs.framework.common.NCLocator;
import nc.bs.logging.Log;
import nc.bs.mmpac.pmo.pac0002.bp.service.PMOBPService;
import nc.bs.uapbd.util.ThirdPartyPostRequestUtil;
import nc.impl.pubapp.pattern.rule.IRule;
import nc.itf.bd.material.baseinfo.IMaterialBaseInfoQueryService;
import nc.jdbc.framework.processor.ColumnProcessor;
import nc.pubitf.para.SysInitQuery;
import nc.util.mmf.framework.base.MMValueCheck;
import nc.vo.bd.defdoc.DefdocVO;
import nc.vo.bd.material.MaterialVO;
import nc.vo.cmp.util.StringUtils;
import nc.vo.mmpac.pmo.pac0002.entity.PMOAggVO;
import nc.vo.mmpac.pmo.pac0002.entity.PMOHeadVO;
import nc.vo.mmpac.pmo.pac0002.entity.PMOItemVO;
import nc.vo.org.OrgVO;
import nc.vo.pub.BusinessException;
import nc.vo.pub.lang.UFBoolean;
import nc.vo.pubapp.pattern.exception.ExceptionUtils;
import nc.vo.pubapp.pattern.pub.SqlBuilder;
import nc.vo.scmpub.util.ArrayUtil;
import nc.vo.util.CloneUtil;

import java.util.*;

/**
 * 流程生产订单审批后推送RZ
 */
public class AfterApprovingSynchronizeRuleRZ implements IRule<PMOAggVO> {
    private static final Log log = Log.getInstance("rzmomlog");
    private static final BaseDAO dao = new BaseDAO();

    private Boolean flag;

    public AfterApprovingSynchronizeRuleRZ(Boolean flag) {
        this.flag = flag;
    }

    @Override
    public void process(PMOAggVO[] pmoAggVOS) {
        if (ArrayUtil.isEmpty(pmoAggVOS)) {
            return;
        }
        try {
            PMOAggVO[] cloneOrderVOS = (PMOAggVO[]) CloneUtil.deepClone(pmoAggVOS);
            // 检查并筛选生产订单
            List<PMOAggVO> filteredOrders = checkAndFilterBillSrcOrg(cloneOrderVOS);
            if (filteredOrders.isEmpty()) {
                return;
            }

            // 推送到锐制系统
            pushToRZMOM(filteredOrders.toArray(new PMOAggVO[0]));
        } catch (Exception e) {
            log.error("同步生产订单到RZ系统失败: " + e.getMessage());
            ExceptionUtils.wrappException(e);
        }
    }

    /**
     * 检查并筛选需要同步的单据
     */
    private List<PMOAggVO> checkAndFilterBillSrcOrg(PMOAggVO[] pmoAggVOS) throws BusinessException {
        List<PMOAggVO> aggvoList = new ArrayList<>();
        List<String> tranidList = new ArrayList<String>();
        List<PMOAggVO> finalList = new ArrayList<>();
        for (PMOAggVO aggvo : pmoAggVOS) {
            PMOHeadVO headvo = aggvo.getParentVO();
            String tranid = headvo.getCtrantypeid();
            if (!MMValueCheck.isEmpty(tranid)) {
                tranidList.add(tranid);
            }
        }
        Map<String, UFBoolean> bSaveApproveMap =new HashMap<>();
        if (tranidList.size() > 0) {
             bSaveApproveMap = PMOBPService.getIPMOTransTypeQueryService()
                    .getBSaveApproveByTranTypeIDs(tranidList.toArray(new String[0]));
        }
        for (PMOAggVO aggvo : pmoAggVOS) {
            String pkOrg = aggvo.getParentVO().getPk_org();
            Integer fbillstatus = aggvo.getParentVO().getFbillstatus();
            String tranid = aggvo.getParentVO().getCtrantypeid();
            String orgCode = transferCodeByPk(OrgVO.getDefaultTableName(), OrgVO.CODE, OrgVO.PK_ORG, pkOrg);
            String vtrantypecode = aggvo.getParentVO().getVtrantypecode();
            if(!"55A2-Cxx-01".equals(vtrantypecode)){
                if(this.flag){
                    if ("C022".equals(orgCode) && 1 == fbillstatus&&aggvo.getChildrenVO()!=null && aggvo.getChildrenVO().length>0) {
                        aggvoList.add(aggvo);
                    }
                }else{
                    if ("C022".equals(orgCode)&& 1 == fbillstatus&&aggvo.getChildrenVO()!=null && aggvo.getChildrenVO().length > 0 && !bSaveApproveMap.isEmpty()&&!bSaveApproveMap.getOrDefault(tranid, UFBoolean.FALSE).booleanValue()) {
                        aggvoList.add(aggvo);
                    }
                }
            }
        }
        //再次筛选
        //2025年7月2日10点33分--新增不传--表体物料编码前三位为103时不传
        //获取表体物料信息
        if(aggvoList.isEmpty()){
            return aggvoList;
        }
        Set<String> materialpks=new HashSet<>();
        for (PMOAggVO aggvo : aggvoList) {
            for (PMOItemVO item : aggvo.getChildrenVO()) {
                String cbmaterialvid = item.getCmaterialvid();
                materialpks.add(cbmaterialvid);
            }
        }
        if(materialpks.isEmpty()){
            return aggvoList;
        }
        //根据物料id查询物料信息
        MaterialVO[] vos = NCLocator.getInstance().lookup(IMaterialBaseInfoQueryService.class).queryDataByPks(materialpks.toArray(new String[0]));
        //组装Map
        Map<String, String> materialMap = new HashMap<>();
        if(vos==null || vos.length<1){
            throw new BusinessException("Failed to query material info , please check !!!");
        }
        for (MaterialVO vo : vos) {
            String cmaterialvid = vo.getPk_material();
            String cmaterialcode =vo.getCode();
            materialMap.put(cmaterialvid, cmaterialcode);
        }
        //筛选行数据
        for (PMOAggVO aggvo : aggvoList) {
            List<PMOItemVO> newItems = new ArrayList<>();
            PMOItemVO[] items = (PMOItemVO[]) aggvo.getChildren(PMOItemVO.class);
            for (PMOItemVO item : items) {
                String cmaterialvid = item.getCmaterialvid();
                if (materialMap.containsKey(cmaterialvid)) {
                    String materialCode = materialMap.get(cmaterialvid);
                    if(!materialCode.startsWith("103")){
                        newItems.add(item);
                    }
                }
            }
            if (!newItems.isEmpty()) {
                aggvo.setChildren(PMOItemVO.class,newItems.toArray(new PMOItemVO[0]));
                finalList.add(aggvo);
            }
        }
        return finalList;
    }

    /**
     * 推送数据到RZMOM系统
     */
    private void pushToRZMOM(PMOAggVO[] pmoAggVOS) throws BusinessException {
        String rzwmsip = SysInitQuery.getParaString("GLOBLE00000000000000", "RZWMSIP");
        JSONObject jsonObject = new JSONObject();
        jsonObject.put("dataflow", "用友BIP→RZMOMv6");
        jsonObject.put("actionCode", "jhmxb");  // 生产订单的action code

        JSONObject dataIn = new JSONObject();
        JSONObject dataIn2 = new JSONObject();
        JSONArray details = new JSONArray();

        // 单笔/批量按明细传
        for (PMOAggVO pmoAggVO : pmoAggVOS) {
            PMOHeadVO head = pmoAggVO.getParentVO();
            PMOItemVO[] bodys = pmoAggVO.getChildrenVO();

            // 构建需要同步的数据
            buildSyncData(head, bodys, details);
        }

        dataIn2.put("Details", details);
        dataIn.put("Data", dataIn2);
        jsonObject.put("data", dataIn);

        log.error("生产订单审批推送锐制请求报文：" + jsonObject.toJSONString());

        String result = ThirdPartyPostRequestUtil.sendPostRequest(rzwmsip, jsonObject.toJSONString());
        JSONObject resultObj = JSONObject.parseObject(result);
        if ("false".equals(resultObj.getString("success"))) {
            throw new BusinessException("RZMOM同步失败，原因：" + resultObj.getString("msg"));
        }else{
            log.error("RZMOM同步成功，返回参数【"+resultObj.toJSONString()+"】");
        }
    }

    /**
     * 构建同步数据
     */
    private void buildSyncData(PMOHeadVO head, PMOItemVO[] bodys, JSONArray details) throws BusinessException {
        String vbillcode = head.getVbillcode();  // 单据号

        for (PMOItemVO body : bodys) {
            JSONObject detailItem = new JSONObject();
//            jhmx_wbid	varchar(100)	第三方系统主键id	必填	上位系统后台唯一ID
            detailItem.put("jhmx_wbid", head.getCpmohid() + "_" + body.getCmoid());

//计划ID	必填	用于标识哪些数据属于同一个生产计划下	 	cpmohid
            detailItem.put("scjh_wbid", head.getCpmohid());

//            操作状态	必填	1新增/修改、2删除（删除时只需上传wbid）
            detailItem.put("operate", 1);
            //            计划编号	必填	前台计划编号
            detailItem.put("jhbh", vbillcode);
            //jhxh	numeric(5)	计划序号	必填	生产订单的产品行号，有按实际。
            detailItem.put("jhxh", body.getVrowno());
            // 第三方系统计划类别id
            detailItem.put("jhlb_wbid", head.getVtrantypecode());



            // 第三方系统产品ID 物料ID
//            detailItem.put("wlbm_wbid", transferCodeByPk(MaterialVO.getDefaultTableName(), MaterialVO.CODE, MaterialVO.PK_MATERIAL, body.getCmaterialvid()));
            detailItem.put("wlbm_wbid", body.getCmaterialvid());
            // 预计开工日期
            if (body.getTplanstarttime() != null) {
                detailItem.put("sxrq", body.getTplanstarttime().toString());
            }
            // 预计完工日期
            if (body.getTplanendtime() != null) {
                detailItem.put("wcrq", body.getTplanendtime().toString());
            }
//            bzsm	varchar(400)	备注说明
            detailItem.put("bzsm", body.getVnote());
//            qfbj	int	签发标记	 	默认0；上位ERP签发后传MOM时，签发仍=0；
            //默认1
            detailItem.put("qfbj", 1);
            // 计划产出数量
            detailItem.put("jhsl", body.getNmmastnum().getDouble());
            //jhlx	int	计划类型	必填	0成品入库、1半成品入库
            //有销售订单号的默认为0；属于零部件生产计划的默认为1；
//            detailItem.put("jhlx", body.getVsalebillcode() == null ? 1 : 0);
            detailItem.put("jhlx", 1);
            // 入库仓库
//            detailItem.put("sdck", transferCodeByPk(StordocVO.getDefaultTableName(), StordocVO.CODE, StordocVO.PK_STORDOC, body.getCinwarehouseid()));
            detailItem.put("sdck", body.getCinwarehouseid());
//            detailItem.put("wlzdycs01", transferCodeByPk(StordocVO.getDefaultTableName(), StordocVO.CODE, StordocVO.PK_STORDOC, body.getCinwarehouseid()));
//            detailItem.put("wlzdycs01", body.getCinwarehouseid());
            //khbh_wbid	varchar(100)	第三方系统客户id	 	 	 	 	BIP生产订单接口增加客户id字段
            detailItem.put("khbh_wbid",body.getCcustomerid());

            // 工作中心 生产部门ID
//            detailItem.put("scgc_wbid", transferCodeByPk(DeptVO.getDefaultTableName(), DeptVO.CODE, DeptVO.PK_DEPT, body.getCdeptid()));
            detailItem.put("scgc_wbid", body.getCdeptid());
            detailItem.put("cjbz_wbid", body.getCdeptid());

            // 备注说明
            detailItem.put("bzsm", body.getVnote());
            //zdscjhlyb	int	自动生成计划来源表	必填	默认传1	 	1
            detailItem.put("zdscjhlyb", 1);
            //如果直接把第三方系统的编号作为我们的计划编号传0，如果我们系统自己取号则传1。
            detailItem.put("jhbhzdsc", 0);

            // 项目编号
            detailItem.put("wlzdycs06", transferCodeByPk("bd_defdoc", DefdocVO.CODE, DefdocVO.PK_DEFDOC, body.getVdef1()));
//            detailItem.put("wlzdycs06", body.getVdef1());
            details.add(detailItem);
        }
    }

    /**
     * 根据主键查询编码
     */
    private String transferCodeByPk(String tableName, String selectField, String pkField, String pk) throws BusinessException {
        if (StringUtils.isEmpty(pk)) {
            return null;
        }
        SqlBuilder sqlBuilder = new SqlBuilder();
        sqlBuilder.append(" select " + selectField);
        sqlBuilder.append(" from " + tableName);
        sqlBuilder.append(" where ");
        sqlBuilder.append(pkField, pk);
        Object o = dao.executeQuery(sqlBuilder.toString(), new ColumnProcessor());
        if (o == null) {
            throw new BusinessException("未查询到编码信息，sql【" + sqlBuilder + "】");
        }
        return o.toString();
    }
}
