diff --git a/arap/src/private/nc/bs/sc/m61/referred/rule/pm/AfterApproceRuleSyncRZWMSProcess.java b/arap/src/private/nc/bs/sc/m61/referred/rule/pm/AfterApproceRuleSyncRZWMSProcess.java new file mode 100644 index 0000000..288284d --- /dev/null +++ b/arap/src/private/nc/bs/sc/m61/referred/rule/pm/AfterApproceRuleSyncRZWMSProcess.java @@ -0,0 +1,151 @@ +package nc.bs.sc.m61.referred.rule.pm; + + +import com.alibaba.fastjson.JSONArray; +import com.alibaba.fastjson.JSONObject; +import nc.bs.dao.BaseDAO; +import nc.bs.logging.Log; +import nc.bs.uapbd.util.ThirdPartyPostRequestUtil; +import nc.impl.pubapp.pattern.rule.IRule; +import nc.jdbc.framework.processor.ColumnProcessor; +import nc.pubitf.para.SysInitQuery; +import nc.vo.bd.material.MaterialVO; +import nc.vo.bd.psn.PsndocVO; +import nc.vo.bd.stordoc.StordocVO; +import nc.vo.bd.supplier.SupplierVO; +import nc.vo.cmp.util.StringUtils; +import nc.vo.org.OrgVO; +import nc.vo.pub.BusinessException; +import nc.vo.pub.lang.UFDouble; +import nc.vo.pubapp.pattern.exception.ExceptionUtils; +import nc.vo.pubapp.pattern.pub.SqlBuilder; +import nc.vo.sc.m61.entity.SCOrderHeaderVO; +import nc.vo.sc.m61.entity.SCOrderItemVO; +import nc.vo.sc.m61.entity.SCOrderVO; +import nc.vo.scmpub.util.ArrayUtil; + +import java.util.ArrayList; +import java.util.List; + +public class AfterApproceRuleSyncRZWMSProcess implements IRule { + + private static Log log = Log.getInstance("rzmomlog"); + + private static BaseDAO dao = new BaseDAO(); + + @Override + public void process(SCOrderVO[] vos) { + if (ArrayUtil.isEmpty(vos)) { + return; + } + try { + //检查并筛选销售出库单据为互感器公司 + List newSCOrderVOS = checkAndFilterBillSrcOrg(vos); + if (newSCOrderVOS == null || newSCOrderVOS.size() < 1) { + return; + } + pushToRZMOM(newSCOrderVOS.toArray(new SCOrderVO[0])); + } catch (Exception e) { + ExceptionUtils.wrappException(e); + } + } + + private void buildSyncData(SCOrderHeaderVO head, SCOrderItemVO[] bodys, JSONArray details) throws BusinessException { + + for (SCOrderItemVO body : bodys) { + JSONObject singleObj = new JSONObject(); + //操作状态 1新增/修改、2删除(删除时只需上传wbid) + singleObj.put("operate", 1); + // 单据类型 + singleObj.put("cgjh_wbid", body.getVsrctrantype()); // 第三方系统采购计划id + singleObj.put("cgxh", body.getVsrcrowno()); // 采购计划序号 + singleObj.put("cgbh", body.getVsrccode()); // 采购计划编号 + singleObj.put("bzsm", body.getVbmemo()); // 备注说明 + singleObj.put("cght_wbid", head.getVbillcode()); // 第三方系统合同ID + singleObj.put("htxsbh", head.getVbillcode()); // 合同编号 + // 供应商 + singleObj.put("zbxx_gycs_wbid", transferCodeByPk(SupplierVO.getDefaultTableName(), SupplierVO.CODE, SupplierVO.PK_SUPPLIER, head.getPk_supplier())); // 第三方系统厂商id + // 仓库 + singleObj.put("sdck", transferCodeByPk(StordocVO.getDefaultTableName(), StordocVO.CODE, StordocVO.PK_STORDOC, body.getPk_recvstordoc())); // 送达仓库 + // 物料 + singleObj.put("wlbm_wbid", transferCodeByPk(MaterialVO.getDefaultTableName(), MaterialVO.CODE, MaterialVO.PK_MATERIAL, body.getPk_material())); // 第三方系统材料id + + UFDouble nqtunitnum = body.getNqtunitnum() == null ? UFDouble.ZERO_DBL : body.getNqtunitnum(); + singleObj.put("cgsl", nqtunitnum.getDouble()); // 采购数量 + if (body.getDplanarrvdate() != null) { + singleObj.put("jhrq", body.getDplanarrvdate().toString()); // 交货日期 + } + if (head.getDbilldate() != null) { + singleObj.put("zbxx_cgrq", head.getDbilldate().toString()); // 采购日期 + } + if (head.getDbilldate() != null) { + singleObj.put("cgrq", head.getDbilldate().toString()); // 采购日期 + } + + singleObj.put("htxh", body.getCrowno()); // 合同序号 + singleObj.put("zbxx_cgy_wbid", transferCodeByPk(PsndocVO.getDefaultTableName(), PsndocVO.CODE, PsndocVO.PK_PSNDOC, head.getCemployeeid())); // 第三方系统采购员id + + + details.add(singleObj); + } + } + + private List checkAndFilterBillSrcOrg(SCOrderVO[] SCOrderVOS) throws BusinessException { + List aggvoList = new ArrayList<>(); + for (SCOrderVO aggvo : SCOrderVOS) { + String pkOrg = aggvo.getParentVO().getPk_org(); + Integer fstatusflag = aggvo.getParentVO().getFstatusflag(); + String orgCode = transferCodeByPk(OrgVO.getDefaultTableName(), OrgVO.CODE, OrgVO.PK_ORG, pkOrg); + if ("30401".equals(orgCode) && 3 == fstatusflag) { + aggvoList.add(aggvo); + } + } + return aggvoList; + } + + private void pushToRZMOM(SCOrderVO[] SCOrderVOS) throws BusinessException { + String rzwmsip = SysInitQuery.getParaString("GLOBLE00000000000000", "RZWMSIP"); + JSONObject jsonObject = new JSONObject(); + JSONObject data = new JSONObject(); + JSONObject dataIn = new JSONObject(); + JSONObject dataIn2 = new JSONObject(); + JSONArray details = new JSONArray(); + jsonObject.put("dataflow", "泰开BIP→RZMOMv6"); + jsonObject.put("actionCode", "htmxb"); + //单笔/批量按明细传 + for (SCOrderVO SCOrderVO : SCOrderVOS) { + SCOrderHeaderVO head = SCOrderVO.getParentVO(); + SCOrderItemVO[] bodys = SCOrderVO.getChildrenVO(); + // 构建需要同步的数据 + buildSyncData(head, bodys, details); + } + dataIn2.put("Details", details); + dataIn.put("Data", dataIn2); + data.put("data", dataIn); + jsonObject.put("data", data); + 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")); + } + } + + 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(); + } + + +} diff --git a/arap/src/private/nc/impl/sc/m61/action/approve/SCOrderApproveAction.java b/arap/src/private/nc/impl/sc/m61/action/approve/SCOrderApproveAction.java new file mode 100644 index 0000000..393e69c --- /dev/null +++ b/arap/src/private/nc/impl/sc/m61/action/approve/SCOrderApproveAction.java @@ -0,0 +1,103 @@ +package nc.impl.sc.m61.action.approve; + + +import nc.bs.pub.compiler.AbstractCompiler2; +import nc.bs.sc.m61.referred.rule.ic.ApproveSupplyRule; +import nc.bs.sc.m61.referred.rule.pm.SCOrderApprovePMSupplyRule; +import nc.bs.sc.m61.referred.rule.pm.SCOrderRewritePMStartDateRule; +import nc.bs.sc.plugin.SCOrderPluginPoint; +import nc.bs.scmpub.pf.PfParameterUtil; +import nc.bs.scmpub.rule.VOSagaFrozenValidateRule; +import nc.impl.pubapp.pattern.data.bill.BillUpdate; +import nc.impl.pubapp.pattern.rule.processer.CompareAroundProcesser; +import nc.impl.sc.m61.action.approve.rule.*; +import nc.itf.sc.m61.compenstate.IScOrderPmSagasCompensate; +import nc.itf.sc.reference.ic.ATPServices; +import nc.vo.pub.BusinessException; +import nc.vo.pubapp.pattern.exception.ExceptionUtils; +import nc.vo.sc.m61.entity.SCOrderVO; +import nc.vo.sc.m61.entity.context.SCOrderContxt; +import nc.vo.sc.pub.enumeration.SCBillStatus; +import nc.vo.scmpub.msg.rule.UpdateMsgStatusRule; +import nc.vo.scmpub.res.billtype.SCBillType; +import nc.vo.scmpub.util.AppInfoContext; +import nccloud.commons.lang.ArrayUtils; +import nccloud.pubitf.pu.pub.util.PuSagasUtil; +import nccloud.pubitf.sc.pub.util.SCOperationEnum; +import nccloud.pubitf.sc.pub.util.SCSagasOperationEnum; +import nccloud.pubitf.sc.pub.util.ScSagasUtil; +import nc.bs.sc.m61.referred.rule.pm.AfterApproceRuleSyncRZWMSProcess; +import java.io.Serializable; +import java.util.HashMap; +import java.util.Map; + +public class SCOrderApproveAction { + + private void addRule(CompareAroundProcesser prcr) { + prcr.addBeforeRule(new VOSagaFrozenValidateRule(true)); + prcr.addBeforeFinalRule(new ApproveStatusChkRule()); + prcr.addBeforeFinalRule(new SupplierFrozeChkRule()); + prcr.addBeforeFinalRule(new UpdateMsgStatusRule("pk_order")); + prcr.addBeforeRule(new ApproveFlowCheckMnyRule()); + prcr.addAfterFinalRule(new UpdatePFlowInfoRule()); + prcr.addAfterRule(new FilterOrderByStatusRule(SCBillStatus.APPROVED.toInt())); + prcr.addAfterRule(new SCOrderRewritePMStartDateRule(true)); + prcr.addAfterRule(new ApproveSupplyRule()); + prcr.addAfterRule(new SCOrderApprovePMSupplyRule()); + + //2025年5月18日15点12分--互感器委外订单审批推送RZ系统 + prcr.addAfterRule(new AfterApproceRuleSyncRZWMSProcess()); + } + + public SCOrderVO[] approve(SCOrderVO[] vos, SCOrderContxt contxt, AbstractCompiler2 script) { + if (ArrayUtils.isEmpty(vos)) { + return vos; + } else { + PfParameterUtil util = new PfParameterUtil(script == null ? null : script.getPfParameterVO(), vos); + SCOrderVO[] originBills = (SCOrderVO[]) util.getOrginBills(); + SCOrderVO[] clientBills = (SCOrderVO[]) util.getClientFullInfoBill(); + CompareAroundProcesser prcr = new CompareAroundProcesser(SCOrderPluginPoint.APPROVE); + this.addRule(prcr); + prcr.before(clientBills, originBills); + if (null != script) { + try { + script.procFlowBacth(script.getPfParameterVO()); + } catch (Exception e) { + ExceptionUtils.wrappException(e); + } + } + + this.atpBeforeUpdate(clientBills); + + try { + AppInfoContext.setProductCode(SCSagasOperationEnum.OREDERAPPROVE.getResCommon()); + AppInfoContext.setResId(SCSagasOperationEnum.OREDERAPPROVE.getResId()); + ScSagasUtil.frozenAndAddSaga(vos, "scorderApprove", SCBillType.Order.getCode()); + Map paramMap = new HashMap(); + paramMap.put("actionname", "scorderApprove"); + paramMap.put("hid", originBills[0].getParentVO().getPrimaryKey()); + paramMap.put(SCOperationEnum.APPROVER, originBills[0].getParentVO().getApprover()); + paramMap.put(SCOperationEnum.TAUDITTIME, originBills[0].getParentVO().getTaudittime()); + paramMap.put(SCOperationEnum.FBILLSTATUS, originBills[0].getParentVO().getFstatusflag()); + PuSagasUtil.compensate(IScOrderPmSagasCompensate.class, paramMap); + } catch (BusinessException e) { + ExceptionUtils.wrappException(e); + } + + BillUpdate update = new BillUpdate(); + SCOrderVO[] updateVOs = (SCOrderVO[]) update.update(clientBills, originBills); + prcr.after(clientBills, originBills); + this.atpAfterUpdate(updateVOs); + return updateVOs; + } + } + + private void atpAfterUpdate(SCOrderVO[] updateVOs) { + ATPServices.modifyATPAfter(SCBillType.Order.getCode(), updateVOs); + } + + private void atpBeforeUpdate(SCOrderVO[] clientBills) { + ATPServices.modifyATPBefore(SCBillType.Order.getCode(), clientBills); + } + +} diff --git a/arap/src/public/nc/api/arap/resource/GatheringbillRestResource.java b/arap/src/public/nc/api/arap/resource/GatheringbillRestResource.java index 28fd1ff..ffbb5bd 100644 --- a/arap/src/public/nc/api/arap/resource/GatheringbillRestResource.java +++ b/arap/src/public/nc/api/arap/resource/GatheringbillRestResource.java @@ -270,7 +270,7 @@ public class GatheringbillRestResource extends ArapBaseRestResource { HYSuperDMO dmo = new HYSuperDMO(); SaleOrderHVO[] hvo = (SaleOrderHVO[]) dmo.queryByWhereClause(SaleOrderHVO.class, - "vbillcode='" + def2 + "'"); + "vbillcode='" + def2 + "' and dr=0"); SaleOrderBVO[] bvos = (SaleOrderBVO[]) dmo.queryByWhereClause(SaleOrderBVO.class, "csaleorderid='" + hvo[0].getPrimaryKey() + "'"); if (bvos != null) { diff --git a/ic/src/private/nc/bs/ic/m4c/sign/SignBP.java b/ic/src/private/nc/bs/ic/m4c/sign/SignBP.java index 96970de..5756daa 100644 --- a/ic/src/private/nc/bs/ic/m4c/sign/SignBP.java +++ b/ic/src/private/nc/bs/ic/m4c/sign/SignBP.java @@ -51,8 +51,11 @@ public class SignBP implements ISignBP, ISignRuleProvider processor.addAfterRule(new SaleOutProceedsRuleCG()); processor.addAfterRule(new MobAfterSignMessageRule()); // 销售出库 签字后 同步到MES金思维系统 - processor.addAfterRule(new AfterSigningSynchronizeRule()); + processor.addAfterRule(new AfterSigningSynchronizeRuleMES()); // 盘点(审批后传MES) + + // 销售出库 签字后 同步到锐制 + processor.addAfterRule(new AfterSigningSynchronizeRuleRZ()); } public void addBeforeRule(SaleOutVO[] vos, AroundProcesser processor) { diff --git a/ic/src/private/nc/bs/ic/m4c/sign/rule/AfterSigningSynchronizeRule.java b/ic/src/private/nc/bs/ic/m4c/sign/rule/AfterSigningSynchronizeRuleMES.java similarity index 64% rename from ic/src/private/nc/bs/ic/m4c/sign/rule/AfterSigningSynchronizeRule.java rename to ic/src/private/nc/bs/ic/m4c/sign/rule/AfterSigningSynchronizeRuleMES.java index 9909ce7..93bad7a 100644 --- a/ic/src/private/nc/bs/ic/m4c/sign/rule/AfterSigningSynchronizeRule.java +++ b/ic/src/private/nc/bs/ic/m4c/sign/rule/AfterSigningSynchronizeRuleMES.java @@ -3,27 +3,40 @@ package nc.bs.ic.m4c.sign.rule; import com.alibaba.fastjson.JSONArray; import com.alibaba.fastjson.JSONObject; import com.yonyou.cloud.utils.StringUtils; +import nc.bs.dao.BaseDAO; import nc.bs.framework.common.NCLocator; import nc.bs.logging.Log; import nc.impl.pubapp.pattern.rule.IRule; +import nc.jdbc.framework.processor.ColumnProcessor; +import nc.vo.bd.cust.CustomerVO; +import nc.vo.bd.material.MaterialVO; +import nc.vo.bd.material.measdoc.MeasdocVO; +import nc.vo.bd.psn.PsndocVO; +import nc.vo.bd.rack.RackVO; +import nc.vo.bd.supplier.SupplierVO; import nc.vo.ic.m4c.entity.SaleOutBodyVO; import nc.vo.ic.m4c.entity.SaleOutHeadVO; import nc.vo.ic.m4c.entity.SaleOutVO; +import nc.vo.org.DeptVO; import nc.vo.pub.BusinessException; import nc.vo.pub.lang.UFDate; +import nc.vo.pubapp.pattern.pub.SqlBuilder; import nccloud.pubift.commen.itf.utils.IHttpPostOtherSys; import java.text.SimpleDateFormat; -//销售出库(签字后传MES金思维系统) -public class AfterSigningSynchronizeRule implements IRule { +/** + * 销售出库(签字后传MES金思维系统) + */ +public class AfterSigningSynchronizeRuleMES implements IRule { private static final String SALE_OUT_URL = "/GTHINKING/AjaxService/N_MISPRO/SaleOrderOutbound.ashx/SaveData"; // 销售出库登记接口 private static final SimpleDateFormat dateTimeFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); private static final String logginfo = "OALOG"; private static final Log obmlog = Log.getInstance(logginfo); + private static BaseDAO dao = new BaseDAO(); - public AfterSigningSynchronizeRule() { + public AfterSigningSynchronizeRuleMES() { } @Override @@ -57,9 +70,9 @@ public class AfterSigningSynchronizeRule implements IRule { * 构建符合金思维系统接口规范的请求数据 * 按照NCC/YonBIP字段映射到金思维系统字段 */ - private JSONObject buildSyncData(SaleOutHeadVO hvo, SaleOutBodyVO[] bvos) { + private JSONObject buildSyncData(SaleOutHeadVO hvo, SaleOutBodyVO[] bvos) throws BusinessException { obmlog.debug("AfterSigningSynchronizeRule-开始处理销售出库单: " + hvo.getVbillcode()); - if (!hvo.getPk_org().equals("0001A1100000000026O5") || !hvo.getPk_org().equals("1001A11000000KFE18FO")) { + if (!hvo.getPk_org().equals("0001A110000000000677")) { obmlog.debug("AfterSigningSynchronizeRule-跳过处理销售出库单,因为此单据组织非电缆: " + hvo.getVbillcode()); return null; } @@ -71,43 +84,33 @@ public class AfterSigningSynchronizeRule implements IRule { info.put("orderNo", hvo.getVbillcode()); // 提货单ID - 单据号(vbillcode) // 日期格式转换 UFDate dbilldate = hvo.getDbilldate(); - String billDateStr = dateTimeFormat.format(dbilldate.toDate()); - info.put("orderDate", billDateStr); // 提单日期 - 单据日期(dbilldate) - info.put("planDate", billDateStr); // 计划日期 - 使用同样的单据日期 - info.put("actureDate", billDateStr); - // 生成方式可能存储在自定义字段中 - String genType = getStringValue(hvo.getVdef1()); - info.put("genType", null); // 生成方式 - 默认N - info.put("type", "XSCK"); // 默认事务类型XSCK - info.put("departmentId", hvo.getCdptvid()); // 部门ID - 部门(cdptvid) - info.put("storeId", hvo.getCwarehouseid()); // 仓库ID - 仓库(cwarehouseid) - // 汇率默认为1 + info.put("orderDate", dbilldate.toString()); // 提单日期 - 单据日期(dbilldate) + info.put("planDate", dbilldate.toString()); // 计划日期 - 使用同样的单据日期 + info.put("actureDate", dbilldate.toString()); + info.put("genType", null); + info.put("type", "XSCK"); + // 部门ID - 部门(cdptvid) + info.put("departmentId", transferCodeByPk(DeptVO.getDefaultTableName(), DeptVO.CODE, DeptVO.PK_DEPT, hvo.getCdptvid())); + // 仓库ID - 仓库(cwarehouseid) + info.put("storeId", transferCodeByPk(RackVO.getDefaultTableName(), RackVO.CODE, RackVO.PK_RACK, hvo.getCwarehouseid())); + // TODO info.put("exRate", null); info.put("sType", "N"); // 发出默认值 info.put("billing", "Y"); // 出具发票默认值 info.put("billingBasis", "S"); // 开票依据默认值 - - // 有效日期可能为空,可能存储在其他字段或自定义字段中 - String effDateStr = getStringValue(hvo.getVdef2()); - if (StringUtils.isNotEmpty(effDateStr)) { - try { - UFDate effDate = new UFDate(effDateStr); - info.put("effDate", dateTimeFormat.format(effDate.toDate())); - } catch (Exception e) { - obmlog.error("解析有效日期出错: " + e.getMessage()); - } - } - + info.put("effDate", null); info.put("consignStoreId", null); // 寄售仓库ID info.put("consignType", null); // 寄售事务类型 info.put("operatorNo", null); // 经办人工号 - 制单人(billmaker) - info.put("operatorName", null); // 经办人 - 可能是自定义字段 - info.put("storeKeeper", hvo.getCwhsmanagerid()); // 保管员 - 库管员(cwhsmanagerid) - info.put("cwhsmanagerid", hvo.getCwhsmanagerid()); // 保管员ID - 库管员(cwhsmanagerid) - info.put("customId", hvo.getCcustomerid()); // 客户ID - 订单客户(ccustomerid) + info.put("operatorName", null); // 经办人 + // 保管员 - 库管员(cwhsmanagerid) + info.put("storeKeeper", transferCodeByPk(PsndocVO.getDefaultTableName(), PsndocVO.CODE, PsndocVO.PK_PSNDOC, hvo.getCwhsmanagerid())); + // 保管员ID - 库管员(cwhsmanagerid) + info.put("cwhsmanagerid", transferCodeByPk(PsndocVO.getDefaultTableName(), PsndocVO.CODE, PsndocVO.PK_PSNDOC, hvo.getCwhsmanagerid())); + // 客户ID - 订单客户(ccustomerid) + info.put("customId", transferCodeByPk(CustomerVO.getDefaultTableName(), CustomerVO.CODE, CustomerVO.PK_CUSTOMER, hvo.getCcustomerid())); info.put("mark", "Y"); // 生成标志默认值 info.put("remark", hvo.getVnote()); // 备注 - 备注(vnote) - // 构建details明细数组 JSONArray details = new JSONArray(); if (bvos != null) { @@ -115,32 +118,32 @@ public class AfterSigningSynchronizeRule implements IRule { JSONObject detail = new JSONObject(); detail.put("orderNo", hvo.getVbillcode()); // 提货单ID - 单据号(vbillcode) detail.put("sequenceNum", bvo.getCrowno()); - // 来源单据信息 - 根据字典正确映射 detail.put("saleOrderNo", null); // SOID - 来源单据号(vsourcebillcode) detail.put("saleSequenceNum", null); // SO序号 - 来源单据行号(vsourcerowno) detail.put("allocationNum", null); // 分配号 - - // 物料相关 - 使用正确的字段名 - detail.put("materialId", bvo.getCmaterialoid()); // 物料ID - 物料(cmaterialoid) - detail.put("unit", bvo.getCunitid()); // 计量单位 - 主单位(cunitid) - detail.put("productNum", null); // 制令号 - 可能是自定义字段 - - detail.put("storageId", bvo.getClocationid()); // 库位 - 货位(clocationid) - detail.put("batchNum", bvo.getVbatchcode()); // 物料批号 - 批次号(vbatchcode) + // 物料ID - 物料(cmaterialoid) + detail.put("materialId", transferCodeByPk(MaterialVO.getDefaultTableName(), MaterialVO.CODE, MaterialVO.PK_MATERIAL, bvo.getCmaterialoid())); + // 计量单位 - 主单位(cunitid) + detail.put("unit", transferCodeByPk(MeasdocVO.getDefaultTableName(), MeasdocVO.CODE, MeasdocVO.PK_MEASDOC, bvo.getCunitid())); + detail.put("productNum", null); + // 库位 - 货位(clocationid) + detail.put("storageId", transferCodeByPk(RackVO.getDefaultTableName(), RackVO.CODE, RackVO.PK_RACK, bvo.getClocationid())); + // 物料批号 - 批次号(vbatchcode) + detail.put("batchNum", bvo.getVbatchcode()); detail.put("scaleFactor", bvo.getVchangerate()); - // 应发数量和实发数量 detail.put("issuedQty", bvo.getNshouldassistnum()); // 应发数量(nshouldassistnum) detail.put("mIssuedQty", bvo.getNshouldnum()); // 主应发数量(nshouldnum) detail.put("actQry", bvo.getNassistnum()); // 实发数量(nassistnum) detail.put("mActQry", bvo.getNnum()); // 主实发数量(nnum) detail.put("assistActQry", null); // 辅助实发数量(nassistnum) - // 客户信息 - detail.put("customId", getStringValue(bvo.getCasscustid())); // 客户ID - 客户(casscustid) + // 客户ID - 客户(casscustid) + detail.put("customId", transferCodeByPk(CustomerVO.getDefaultTableName(), CustomerVO.CODE, CustomerVO.PK_CUSTOMER, bvo.getCasscustid())); // 供应商信息 - detail.put("supplierId", getStringValue(bvo.getCvendorid())); // 供应商ID - 供应商(cvendorid) + // 供应商ID - 供应商(cvendorid) + detail.put("supplierId", transferCodeByPk(SupplierVO.getDefaultTableName(), SupplierVO.CODE, SupplierVO.PK_SUPPLIER, bvo.getCvendorid())); detail.put("color", null); // 生产日期 detail.put("manufactureDate", null); // 生产日期(dproducedate) @@ -194,4 +197,21 @@ public class AfterSigningSynchronizeRule implements IRule { obmlog.error("AfterSigningSynchronizeRule-处理响应异常: " + e.getMessage(), e); } } + + + private String transferCodeByPk(String tableName, String selectField, String pkField, String pk) throws BusinessException { + if (nc.vo.cmp.util.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(); + } } diff --git a/ic/src/private/nc/bs/ic/m4c/sign/rule/AfterSigningSynchronizeRuleRZ.java b/ic/src/private/nc/bs/ic/m4c/sign/rule/AfterSigningSynchronizeRuleRZ.java new file mode 100644 index 0000000..52aad8a --- /dev/null +++ b/ic/src/private/nc/bs/ic/m4c/sign/rule/AfterSigningSynchronizeRuleRZ.java @@ -0,0 +1,161 @@ +package nc.bs.ic.m4c.sign.rule; + +import com.alibaba.fastjson.JSONArray; +import com.alibaba.fastjson.JSONObject; +import nc.bs.dao.BaseDAO; +import nc.bs.logging.Log; +import nc.bs.uapbd.util.ThirdPartyPostRequestUtil; +import nc.impl.pubapp.pattern.rule.IRule; +import nc.jdbc.framework.processor.ColumnProcessor; +import nc.pubitf.para.SysInitQuery; +import nc.vo.bd.cust.CustomerVO; +import nc.vo.bd.material.MaterialVO; +import nc.vo.bd.stordoc.StordocVO; +import nc.vo.cmp.util.StringUtils; +import nc.vo.ic.m4c.entity.SaleOutBodyVO; +import nc.vo.ic.m4c.entity.SaleOutHeadVO; +import nc.vo.ic.m4c.entity.SaleOutVO; +import nc.vo.org.DeptVO; +import nc.vo.org.OrgVO; +import nc.vo.pub.BusinessException; +import nc.vo.pub.lang.UFDate; +import nc.vo.pubapp.pattern.exception.ExceptionUtils; +import nc.vo.pubapp.pattern.pub.SqlBuilder; +import nc.vo.scmpub.util.ArrayUtil; + +import java.util.ArrayList; +import java.util.List; + +/** + * @Classname AfterSigningSynchronizeRuleRZ + * @Description TODO + * @Version 1.0.0 + * @Date 2025/5/16 9:01 + * @Created by ame + */ +public class AfterSigningSynchronizeRuleRZ implements IRule { + private static Log log=Log.getInstance("rzmomlog"); + + private static BaseDAO dao = new BaseDAO(); + @Override + public void process(SaleOutVO[] saleOutVOS) { + if(ArrayUtil.isEmpty(saleOutVOS)){ + return; + } + try{ + //检查并筛选销售出库单据为互感器公司 + List newSaleOutVOS= checkAndFilterBillSrcOrg(saleOutVOS); + if(newSaleOutVOS==null||newSaleOutVOS.size()<1){ + return; + } + pushToRZMOM(newSaleOutVOS.toArray(new SaleOutVO[0])); + }catch (Exception e){ + ExceptionUtils.wrappException(e); + } + } + + private List checkAndFilterBillSrcOrg(SaleOutVO[] saleOutVOS) throws BusinessException { + List aggvoList=new ArrayList<>(); + for(SaleOutVO aggvo:saleOutVOS){ + String pkOrg = aggvo.getHead().getPk_org(); + String orgCode = transferCodeByPk(OrgVO.getDefaultTableName(), OrgVO.CODE, OrgVO.PK_ORG, pkOrg); + if("30401".equals(orgCode)){ + aggvoList.add(aggvo); + } + } + return aggvoList; + } + + private void pushToRZMOM(SaleOutVO[] saleOutVOS) throws BusinessException { + String rzwmsip = SysInitQuery.getParaString("GLOBLE00000000000000", "RZWMSIP"); + JSONObject jsonObject = new JSONObject(); + JSONObject data = new JSONObject(); + JSONObject dataIn = new JSONObject(); + JSONObject dataIn2 = new JSONObject(); + JSONArray details = new JSONArray(); + jsonObject.put("dataflow","泰开BIP→RZMOMv6"); + jsonObject.put("actionCode","cpfhtzdb"); + //单笔/批量按明细传 + for (SaleOutVO saleOutVO : saleOutVOS) { + SaleOutHeadVO head = saleOutVO.getHead(); + SaleOutBodyVO[] bodys = saleOutVO.getBodys(); + // 构建需要同步的数据 + buildSyncData(head, bodys,details); + } + dataIn2.put("Details",details); + dataIn.put("Data",dataIn2); + data.put("data",dataIn); + jsonObject.put("data",data); + 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")); + } + } + + private void buildSyncData(SaleOutHeadVO head, SaleOutBodyVO[] bodys, JSONArray details) throws BusinessException { + + String vbillcode = head.getVbillcode();//单据号 + String vtrantypecode = head.getVtrantypecode();//出入库类型编码 + //部门 + String cdptCode =transferCodeByPk(DeptVO.getDefaultTableName(), DeptVO.CODE,DeptVO.PK_DEPT,head.getCdptid()); + + for(SaleOutBodyVO body:bodys){ + JSONObject singleObj = new JSONObject(); + String cgeneralhid = body.getCgeneralhid();//表头主键 + String cgeneralbid = body.getCgeneralbid();//表体主键 + String crowno = body.getCrowno();//行号 + String cmaterialvid = body.getCmaterialvid();//物料 + String casscustid = body.getCasscustid();//客户 + String cbodywarehouseid = body.getCbodywarehouseid();//仓库 + UFDate dbizdate = body.getDbizdate();//出库日期 + singleObj.put("djbh_id",cgeneralhid+"_"+cgeneralbid);//单据id + singleObj.put("djbh",vbillcode);//单据编号 + singleObj.put("djxh",crowno);//单据序号 + singleObj.put("djrq",dbizdate.toString());//单据日期--出库日期 + singleObj.put("wbid",cgeneralhid);//第三方系统主键id + singleObj.put("wbpid",cgeneralbid);//第三方系统分组id + //第三方系统物料名称id--编码 + singleObj.put("wlbm_wbid",transferCodeByPk(MaterialVO.getDefaultTableName(),MaterialVO.CODE,MaterialVO.PK_MATERIAL,cmaterialvid)); + //第三方系统客户id--编码 + singleObj.put("khbh_wbid",transferCodeByPk(CustomerVO.getDefaultTableName(),CustomerVO.CODE,CustomerVO.PK_CUSTOMER,casscustid)); + //送达地点-code + String storeCode = transferCodeByPk(StordocVO.getDefaultTableName(), StordocVO.CODE, StordocVO.PK_STORDOC, cbodywarehouseid); + singleObj.put("sddd",storeCode); + //第三方系统仓库id -code + singleObj.put("ckbh_wbid",storeCode); + //部门 + singleObj.put("bzsm",cdptCode); + //签发标记 + singleObj.put("qfbj",1); + //订单编号 + singleObj.put("ddbh",body.getVsourcebillcode()); + //订单序号 + singleObj.put("ddxh",body.getVsourcerowno()); + //单据数量 + singleObj.put("djsl",body.getNshouldassistnum().getDouble()); + //操作状态 1新增/修改、2删除(删除时只需上传wbid) + singleObj.put("operate",1); + details.add(singleObj); + } + } + + + 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(); + } + +} diff --git a/ic/src/private/nc/bs/ic/m4i/sign/rule/AfterSignRuleSyncMesProcess.java b/ic/src/private/nc/bs/ic/m4i/sign/rule/AfterSignRuleSyncMesProcess.java index 39d1903..a21bda9 100644 --- a/ic/src/private/nc/bs/ic/m4i/sign/rule/AfterSignRuleSyncMesProcess.java +++ b/ic/src/private/nc/bs/ic/m4i/sign/rule/AfterSignRuleSyncMesProcess.java @@ -44,10 +44,10 @@ public class AfterSignRuleSyncMesProcess implements IRule { private void syncOtherSystem(GeneralOutVO generalOutVO) throws BusinessException { obmlog.debug("触发同步其它出库单,出库类型编码:" + generalOutVO.getHead().getVtrantypecode() + "开始拼接数据"); -// if (!generalOutVO.getHead().getPk_org().equals("0001A110000000000677")) { -// obmlog.debug("仅同步山东泰开电缆有限公司,当前组织:" + generalOutVO.getHead().getPk_org()); -// return; // 仅操作山东泰开电缆有限公司 -// } + if (!generalOutVO.getHead().getPk_org().equals("0001A110000000000677")) { + obmlog.debug("仅同步山东泰开电缆有限公司,当前组织:" + generalOutVO.getHead().getPk_org()); + return; // 仅操作山东泰开电缆有限公司 + } // 其它出库 if (generalOutVO.getHead().getVtrantypecode().equals("4I-01")) { @@ -100,6 +100,8 @@ public class AfterSignRuleSyncMesProcess implements IRule { requestData.put("operation_type", "I");// 固定给I 操作 requestData.put("info", info); obmlog.debug("其它出库requestData:" + requestData.toJSONString()); + IHttpPostOtherSys httpService = NCLocator.getInstance().lookup(IHttpPostOtherSys.class); + httpService.sendToExternalSystem("/GTHINKING/AjaxService/N_KCSJJS/101527004.ashx/gt_rec_api_qtckdj", requestData); } // 调拨出库/转库单 if (generalOutVO.getHead().getVtrantypecode().equals("4I-02")) { @@ -167,7 +169,7 @@ public class AfterSignRuleSyncMesProcess implements IRule { obmlog.debug("其它出库requestData:" + requestData.toJSONString()); IHttpPostOtherSys httpService = NCLocator.getInstance().lookup(IHttpPostOtherSys.class); - httpService.sendToExternalSystem("test", requestData); + httpService.sendToExternalSystem("/GTHINKING/AjaxService/N_KCSJJS/101527009.ashx/gt_rec_api_dbckdj", requestData); } } diff --git a/ic/src/private/nc/bs/ic/m4r/approve/ApproveBP.java b/ic/src/private/nc/bs/ic/m4r/approve/ApproveBP.java index edd4eda..6b43f9c 100644 --- a/ic/src/private/nc/bs/ic/m4r/approve/ApproveBP.java +++ b/ic/src/private/nc/bs/ic/m4r/approve/ApproveBP.java @@ -1,6 +1,6 @@ package nc.bs.ic.m4r.approve; -import nc.bs.ic.m4r.approve.rule.AfterApprovingSynchronizeRule; +import nc.bs.ic.m4r.approve.rule.AfterApprovingSynchronizeRuleMES; import nc.bs.ic.m4r.approve.rule.PushInOutBills; import nc.bs.ic.m4r.base.BPPluginPoint; import nc.bs.ic.m4r.insert.rule.InvcountDataCheck; @@ -23,7 +23,7 @@ public class ApproveBP implements IApproveBP, IApproveRuleProvid public void addApproveAfterRule(ICAroundProcesser processor) { processor.addAfterRule(new PushInOutBills()); // 盘点(审批后传MES) - processor.addAfterRule(new AfterApprovingSynchronizeRule()); + processor.addAfterRule(new AfterApprovingSynchronizeRuleMES()); } public void addApproveBeforeRule(ICAroundProcesser processor) { diff --git a/ic/src/private/nc/bs/ic/m4r/approve/rule/AfterApprovingSynchronizeRule.java b/ic/src/private/nc/bs/ic/m4r/approve/rule/AfterApprovingSynchronizeRuleMES.java similarity index 50% rename from ic/src/private/nc/bs/ic/m4r/approve/rule/AfterApprovingSynchronizeRule.java rename to ic/src/private/nc/bs/ic/m4r/approve/rule/AfterApprovingSynchronizeRuleMES.java index e4f7a5e..e420d26 100644 --- a/ic/src/private/nc/bs/ic/m4r/approve/rule/AfterApprovingSynchronizeRule.java +++ b/ic/src/private/nc/bs/ic/m4r/approve/rule/AfterApprovingSynchronizeRuleMES.java @@ -4,28 +4,39 @@ package nc.bs.ic.m4r.approve.rule; import com.alibaba.fastjson.JSONArray; import com.alibaba.fastjson.JSONObject; import com.yonyou.cloud.utils.StringUtils; +import nc.bs.dao.BaseDAO; import nc.bs.framework.common.NCLocator; import nc.bs.logging.Log; import nc.impl.pubapp.pattern.rule.IRule; +import nc.jdbc.framework.processor.ColumnProcessor; +import nc.vo.bd.cust.CustomerVO; +import nc.vo.bd.material.MaterialVO; +import nc.vo.bd.rack.RackVO; +import nc.vo.bd.stordoc.StordocVO; +import nc.vo.bd.supplier.SupplierVO; import nc.vo.ic.m4r.entity.InvCountBillVO; import nc.vo.ic.m4r.entity.InvCountBodyVO; import nc.vo.ic.m4r.entity.InvCountHeaderVO; +import nc.vo.org.DeptVO; import nc.vo.pub.BusinessException; import nc.vo.pub.lang.UFDate; import nc.vo.pub.lang.UFDouble; +import nc.vo.pubapp.pattern.pub.SqlBuilder; import nccloud.pubift.commen.itf.utils.IHttpPostOtherSys; import java.text.SimpleDateFormat; -// 盘点(审批后传MES) -public class AfterApprovingSynchronizeRule implements IRule { - private static final String INV_COUNT_URL = "/GTHINKING/AjaxService/N_MISPRO/InvCount.ashx/SaveData"; // 盘点单同步接口 - private static final SimpleDateFormat dateTimeFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); +/** + * 盘点(审批后传MES) + */ +public class AfterApprovingSynchronizeRuleMES implements IRule { + private static final String INV_COUNT_URL = "/GTHINKING/AjaxService/U20231172_N_XSSJJSA/102397009.ashx/KCPD_INSERT"; // 盘点单同步接口 private static final String logginfo = "OALOG"; private static final Log obmlog = Log.getInstance(logginfo); + private static final BaseDAO dao = new BaseDAO(); - public AfterApprovingSynchronizeRule() { + public AfterApprovingSynchronizeRuleMES() { } @Override @@ -65,81 +76,90 @@ public class AfterApprovingSynchronizeRule implements IRule { */ private JSONObject buildSyncData(InvCountHeaderVO hvo, InvCountBodyVO[] bvos) throws BusinessException { obmlog.debug("AfterApprovingSynchronizeRule-开始处理盘点单: " + hvo.getVbillcode()); - if (!hvo.getPk_org().equals("0001A1100000000026O5") || !hvo.getPk_org().equals("1001A11000000KFE18FO")) { + if (!hvo.getPk_org().equals("0001A110000000000677")) { obmlog.debug("AfterApprovingSynchronizeRule-跳过处理销售出库单,因为此单据组织非电缆: " + hvo.getVbillcode()); return null; } + + // 按照新规范构建请求数据 JSONObject requestData = new JSONObject(); - // 操作类型为新增 - requestData.put("operation_type", "I"); - // 构建info对象 - 按照接口要求设置必填字段 - JSONObject info = new JSONObject(); + // 盘点主信息 盘点单号 为空时自动生成 + requestData.put("PDDH", null); - // 必填字段 - info.put("storeId", hvo.getCwarehouseid()); // 仓库ID(cwarehouseid) - 必填 - info.put("departmentId", hvo.getCdptvid()); // 部门ID(cdptvid) - 必填 + // 获取仓库编码 + String warehouseCode = transferCodeByPk(StordocVO.getDefaultTableName(), StordocVO.CODE, StordocVO.PK_STORDOC, hvo.getCwarehouseid()); + requestData.put("CKID", warehouseCode); + + // 盘点部门编码 + String deptCode = transferCodeByPk(DeptVO.getDefaultTableName(), DeptVO.CODE, DeptVO.PK_DEPT, hvo.getCdptvid()); + requestData.put("BMID", deptCode); + // 盘点人 + requestData.put("PDR", getStringValue(hvo.getCountoperator())); // 日期处理 - 盘点日期 UFDate dcountdate = hvo.getDcountdate(); if (dcountdate != null) { - info.put("date", dateTimeFormat.format(dcountdate.toDate())); // 盘点日期(dcountdate) - 必填 + requestData.put("PDRQ", dcountdate.toString()); // 盘点日期 - 必填 } else { - // 如果盘点日期为空,使用单据日期 - UFDate dbilldate = hvo.getDbilldate(); - if (dbilldate != null) { - info.put("date", dateTimeFormat.format(dbilldate.toDate())); - } else { - // 接口要求此字段必填,如果没有日期则使用当前日期 - info.put("date", dateTimeFormat.format(new java.util.Date())); - } + requestData.put("PDRQ", null); } + // 备注 + requestData.put("BZ", getStringValue(hvo.getVnote())); - // 其他主表字段 - info.put("worker", getStringValue(hvo.getCountoperator())); // 盘点人(countoperator) - info.put("mark", "N"); // 生成标志,默认为N - info.put("remark", getStringValue(hvo.getVnote())); // 备注(vnote) - - // 构建details明细数组 + // 构建明细数组 JSONArray details = new JSONArray(); if (bvos != null) { for (InvCountBodyVO bvo : bvos) { JSONObject detail = new JSONObject(); - - // 必填字段 - // 序号 - 转换为浮点数 - detail.put("sequenceNum", bvo.getCrowno()); // 序号(crowno) - 必填 - detail.put("materialId", getStringValue(bvo.getCmaterialvid())); // 物料ID(cmaterialvid) - 必填 - detail.put("storageId", getStringValue(bvo.getClocationid())); // 库位(clocationid) - 必填 - detail.put("batchNum", getStringValue(bvo.getVbatchcode())); // 物料批号(vbatchcode) - 必填 - - // 盘存数量 - 使用实盘主数量 - UFDouble countNum = bvo.getNcountnum(); - if (countNum != null) { - detail.put("panQty", countNum.doubleValue()); // 盘存数量(ncountnum) - 必填 - } else { - throw new BusinessException("盘存数量不能为空"); + // 获取序号并转换为浮点数 + String crownStr = bvo.getCrowno(); + try { + detail.put("XH", Double.parseDouble(crownStr)); // 序号 - 必填 + } catch (NumberFormatException e) { + detail.put("XH", null); // 默认序号 } + // 物料编码 - 必填 + detail.put("WLID", transferCodeByPk(MaterialVO.getDefaultTableName(), MaterialVO.CODE, MaterialVO.PK_MATERIAL, bvo.getCmaterialvid())); + // 货位 + detail.put("KW", transferCodeByPk(RackVO.getDefaultTableName(), RackVO.CODE, RackVO.PK_RACK, bvo.getClocationid())); + // 物料批号 + detail.put("WLPH", getStringValue(bvo.getVbatchcode())); - detail.put("customId", getStringValue(bvo.getCasscustid())); // 客户ID - detail.put("supplierId", getStringValue(bvo.getCvendorid())); // 供应商ID + // 盘存数量 -> 实盘主数量 + UFDouble pcNum = bvo.getNcountnum(); + // 账面主数量 + UFDouble zmNum = bvo.getNonhandnum(); + if (pcNum != null) { + // 盘存数量 -> 实盘主数量 + detail.put("PCSL", pcNum.getDouble()); + if (zmNum != null) { + // 盘盈数量 -> 账面主数量 - 实盘主数量 + detail.put("PYSL", zmNum.getDouble() - pcNum.getDouble()); + // 盘亏数量 -> 实盘主数量 - 账面主数量 + detail.put("PKSL", pcNum.getDouble() - zmNum.getDouble()); + } else { + detail.put("PYSL", null); + detail.put("PKSL", null); + } + } else { + detail.put("PCSL", null); + detail.put("PYSL", null); + detail.put("PKSL", null); + } + // 盈亏单价 + detail.put("YCDJ", null); + // 盈亏原因 + detail.put("YKYY", getStringValue(bvo.getVnotebody())); + // 客户编码 + detail.put("KHID", transferCodeByPk(CustomerVO.getDefaultTableName(), CustomerVO.CODE, CustomerVO.PK_CUSTOMER, bvo.getCasscustid())); + // 供应商编码 + detail.put("GYSID", transferCodeByPk(SupplierVO.getDefaultTableName(), SupplierVO.CODE, SupplierVO.PK_SUPPLIER, bvo.getCvendorid())); - // 生产日期处理 - detail.put("manufactureDate", null); // 如果没有,传入null - detail.put("color", null); - - // 包装信息(可能来自自定义属性) - detail.put("packLen", null); - detail.put("packSize", null); - // 备注 - detail.put("remark", getStringValue(bvo.getVnotebody())); // 备注(vnotebody) details.add(detail); } } - info.put("details", details); - - // 将info对象添加到请求数据中 - requestData.put("info", info); + requestData.put("DETAILS", details); return requestData; } @@ -180,4 +200,20 @@ public class AfterApprovingSynchronizeRule implements IRule { obmlog.error("AfterApprovingSynchronizeRule-处理响应异常: " + e.getMessage(), e); } } + + private String transferCodeByPk(String tableName, String selectField, String pkField, String pk) throws BusinessException { + if (nc.vo.cmp.util.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(); + } } diff --git a/ic/src/private/nccloud/pubift/commen/impl/utils/HttpPostOtherSysImpl.java b/ic/src/private/nccloud/pubift/commen/impl/utils/HttpPostOtherSysImpl.java index ec6f650..bfdc252 100644 --- a/ic/src/private/nccloud/pubift/commen/impl/utils/HttpPostOtherSysImpl.java +++ b/ic/src/private/nccloud/pubift/commen/impl/utils/HttpPostOtherSysImpl.java @@ -1,18 +1,24 @@ package nccloud.pubift.commen.impl.utils; -import com.alibaba.fastjson.JSONObject; -import nccloud.pubift.commen.itf.utils.IHttpPostOtherSys; -import java.io.BufferedReader; +import com.alibaba.fastjson.JSONObject; +import nc.bs.logging.Log; +import nc.vo.pub.BusinessException; +import nccloud.pubift.commen.itf.utils.IHttpPostOtherSys; +import org.apache.http.Header; +import org.apache.http.HttpEntity; +import org.apache.http.client.methods.CloseableHttpResponse; +import org.apache.http.client.methods.HttpPost; +import org.apache.http.entity.StringEntity; +import org.apache.http.impl.client.CloseableHttpClient; +import org.apache.http.impl.client.HttpClients; +import org.apache.http.util.EntityUtils; + import java.io.IOException; -import java.io.InputStreamReader; -import java.io.OutputStreamWriter; -import java.net.HttpURLConnection; -import java.net.URL; import java.util.HashMap; -import java.util.List; import java.util.Map; + public class HttpPostOtherSysImpl implements IHttpPostOtherSys { private static final String USER_ID = "BIP"; @@ -21,137 +27,131 @@ public class HttpPostOtherSysImpl implements IHttpPostOtherSys { private static final String EP_ID = ""; private static final String LOGIN_URL = "/GTHINKING/AjaxService/N_MISPRO/100208057.ashx/Login"; + private static final String LOG_INFO_NAME = "OALOG"; + + private static final Log obmlog = Log.getInstance(LOG_INFO_NAME); @Override public String callMes(String url, JSONObject json) { -// String leip = SysParaInitQuery.getParaString(PubEnv.getPk_group(), "LEIP"); String mesip = "http://192.168.29.32"; String baseurl = mesip + url; - String cookie = this.getMESToken(mesip); + String tokenValue = this.getMESToken(mesip); Map headers = new HashMap<>(); - headers.put("Set-Cookie", cookie); + if (tokenValue != null) { + headers.put("Cookie", ".ASPXAUTH=" + tokenValue); + } return doPost(baseurl, headers, json); } - private String getMESToken(String leip) { - JSONObject jsonObject = new JSONObject(); - jsonObject.put("userId", USER_ID); - jsonObject.put("password", PASSWORD); - jsonObject.put("clientType", CLIENT_TYPE); - jsonObject.put("epId", EP_ID); - return postCookie(leip + LOGIN_URL, null, jsonObject); + /** + * 发送数据到外部系统 + */ + public void sendToExternalSystem(String apiPath, Map requestData) throws BusinessException { + try { + obmlog.debug("HttpPostOtherSys request :" + JSONObject.toJSONString(requestData)); + JSONObject jsonRequest = new JSONObject(requestData); + String response = callMes(apiPath, jsonRequest); + JSONObject jsonResponse = JSONObject.parseObject(response); + + obmlog.debug("三方接口返回::" + jsonResponse.toJSONString()); + + String success = jsonResponse.getString("Success"); + if ("false".equals(success)) { + String errorMessage = jsonResponse.getString("ErrorMessage"); + if (errorMessage == null) { + errorMessage = "No error message provided by the external system."; + } + throw new BusinessException("同步mes系统失败,错误消息:" + errorMessage); + } + + } catch (BusinessException e) { + throw e; + } catch (Exception e) { + throw new BusinessException("调用外部接口失败:" + e.getMessage(), e); + } } /** * 业务请求post方法 */ - private String doPost(String baseurl, Map map, JSONObject json) { - BufferedReader reader = null; - try { - URL url = new URL(baseurl);// 创建连接 - HttpURLConnection connection = (HttpURLConnection) url.openConnection(); - connection.setDoOutput(true); - connection.setDoInput(true); - connection.setUseCaches(false); - connection.setInstanceFollowRedirects(true); - connection.setRequestMethod("POST"); // 设置请求方式 - // 设置接收数据的格式 - connection.setRequestProperty("Content-Type", "application/json"); // 设置发送数据的格式 - if (map != null) { - for (String key : map.keySet()) { - connection.setRequestProperty(key, map.get(key)); + private String doPost(String baseurl, Map headers, JSONObject jsonPayload) { + try (CloseableHttpClient httpClient = HttpClients.createDefault()) { + HttpPost httpPost = new HttpPost(baseurl); + + // Set standard headers + httpPost.setHeader("Content-Type", "application/json;charset=UTF-8"); + + // Set custom headers from the map + if (headers != null) { + for (Map.Entry entry : headers.entrySet()) { + httpPost.setHeader(entry.getKey(), entry.getValue()); } } - connection.connect(); - // 一定要用BufferedReader 来接收响应, 使用字节来接收响应的方法是接收不到内容的 - OutputStreamWriter out = new OutputStreamWriter(connection.getOutputStream(), "UTF-8"); // UTF-8编码 - if (json != null) { - out.append(json.toString()); + + if (jsonPayload != null) { + StringEntity stringEntity = new StringEntity(jsonPayload.toJSONString(), "UTF-8"); + httpPost.setEntity(stringEntity); } - out.flush(); - out.close(); - // 读取响应 - reader = new BufferedReader(new InputStreamReader(connection.getInputStream(), "UTF-8")); - String line; - String res = ""; - while ((line = reader.readLine()) != null) { - res += line; + + try (CloseableHttpResponse response = httpClient.execute(httpPost)) { + HttpEntity entity = response.getEntity(); + String responseString = EntityUtils.toString(entity, "UTF-8"); + return responseString; } - reader.close(); - return res; - } catch (Exception e) { -// e.printStackTrace(); - throw new RuntimeException(e); + } catch (IOException e) { + // In a real application, use a proper logging framework + // e.printStackTrace(); + throw new RuntimeException("HTTP POST request to " + baseurl + " failed: " + e.getMessage(), e); } } - /** - * 获取cookie的请求post - */ - private String postCookie(String baseurl, Map map, JSONObject json) { - BufferedReader reader = null; - try { - URL url = new URL(baseurl); - HttpURLConnection connection = (HttpURLConnection) url.openConnection(); - connection.setDoOutput(true); - connection.setDoInput(true); - connection.setUseCaches(false); - connection.setInstanceFollowRedirects(true); - connection.setRequestMethod("POST"); - connection.setRequestProperty("Content-Type", "application/json"); + // 提取 .ASPXAUTH 的值 - This method remains unchanged + private String extractAspxAuth(String setCookieHeaderLine) { + // setCookieHeaderLine 是一行完整的 Set-Cookie 响应头,例如: + // ".ASPXAUTH=TOKEN_VALUE; path=/; HttpOnly" + // 或 ".ASPXAUTH=TOKEN_VALUE;" + String[] cookieAttributes = setCookieHeaderLine.split(";"); // 按分号分割 + for (String attribute : cookieAttributes) { + String trimmedAttribute = attribute.trim(); // 去除前后空格 + if (trimmedAttribute.startsWith(".ASPXAUTH=")) { + return trimmedAttribute.substring(".ASPXAUTH=".length()); // 提取等号后的值 + } + } + return null; // 没有找到 .ASPXAUTH + } - if (map != null) { - for (String key : map.keySet()) { - connection.setRequestProperty(key, map.get(key)); + private String getMESToken(String mesIpBase) { + JSONObject jsonObject = new JSONObject(); + jsonObject.put("userId", USER_ID); + jsonObject.put("password", PASSWORD); + jsonObject.put("clientType", CLIENT_TYPE); + jsonObject.put("epId", EP_ID); + + String loginUrl = mesIpBase + LOGIN_URL; + + try (CloseableHttpClient httpClient = HttpClients.createDefault()) { + HttpPost httpPost = new HttpPost(loginUrl); + httpPost.setHeader("Content-Type", "application/json;charset=UTF-8"); + + StringEntity stringEntity = new StringEntity(jsonObject.toJSONString(), "UTF-8"); + httpPost.setEntity(stringEntity); + + try (CloseableHttpResponse response = httpClient.execute(httpPost)) { + Header[] setCookieHeaders = response.getHeaders("Set-Cookie"); + if (setCookieHeaders != null) { + for (Header header : setCookieHeaders) { + String aspxAuthValue = extractAspxAuth(header.getValue()); + if (aspxAuthValue != null) { + return aspxAuthValue; // Found and return .ASPXAUTH token value + } + } } - } - connection.connect(); - - // 写入请求体 - OutputStreamWriter out = new OutputStreamWriter(connection.getOutputStream(), "UTF-8"); - if (json != null) { - out.append(json.toString()); + return null; // Return null if .ASPXAUTH cookie is not found, as per } - out.flush(); - out.close(); + } catch (IOException e) { - // 读取响应头中的 Set-Cookie - Map> headers = connection.getHeaderFields(); - String setCookieHeader = null; - - for (Map.Entry> entry : headers.entrySet()) { - if ("Set-Cookie".equalsIgnoreCase(entry.getKey())) { - setCookieHeader = entry.getValue().get(0); // 取第一个 Set-Cookie 头 - break; - } - } - if (setCookieHeader != null) { - return extractAspxAuth(setCookieHeader); // 返回 ASPXAUTH 的值 - } else { - return null; - } - - } catch (Exception e) { - throw new RuntimeException(e); - } finally { - if (reader != null) { - try { - reader.close(); - } catch (IOException e) { - e.printStackTrace(); - } - } + throw new RuntimeException("Failed to get MESToken (cookie) from " + loginUrl + " due to IO issue: " + e.getMessage(), e); } } - // 提取 .ASPXAUTH 的值 - private String extractAspxAuth(String cookieHeader) { - String[] cookies = cookieHeader.split("; "); - for (String cookie : cookies) { - if (cookie.startsWith(".ASPXAUTH=")) { - return cookie.substring(".ASPXAUTH=".length()); - } - } - return null; - } } diff --git a/ic/src/public/nccloud/pubift/commen/itf/utils/IHttpPostOtherSys.java b/ic/src/public/nccloud/pubift/commen/itf/utils/IHttpPostOtherSys.java index 2b4ba2e..0dfa373 100644 --- a/ic/src/public/nccloud/pubift/commen/itf/utils/IHttpPostOtherSys.java +++ b/ic/src/public/nccloud/pubift/commen/itf/utils/IHttpPostOtherSys.java @@ -1,48 +1,28 @@ package nccloud.pubift.commen.itf.utils; + import com.alibaba.fastjson.JSONObject; -import nc.bs.framework.common.NCLocator; +import nc.bs.logging.Log; import nc.vo.pub.BusinessException; -import java.util.Iterator; import java.util.Map; public interface IHttpPostOtherSys { + String logginfo = "OALOG"; + + Log obmlog = Log.getInstance(logginfo); + /** * @param apiPath MES的接口地址,不包含ip - * @param json 入参 + * @param json 入参 */ public String callMes(String apiPath, JSONObject json); /** * 发送数据到外部系统 */ - default void sendToExternalSystem(String apiPaht, Map requestData) throws BusinessException { - try { - IHttpPostOtherSys httpService = NCLocator.getInstance().lookup(IHttpPostOtherSys.class); - JSONObject jsonRequest = new JSONObject(requestData); - String response = httpService.callMes(apiPaht, jsonRequest); - JSONObject jsonResponse = JSONObject.parseObject(response); + public void sendToExternalSystem(String apiPaht, Map requestData) throws BusinessException; - int code = jsonResponse.getIntValue("code"); - if (code != 0) { - throw new Exception("自定义档案同步失败,错误码:" + code + ",消息:" + jsonResponse.getString("message")); - } - - if (jsonResponse.containsKey("data") && !jsonResponse.getJSONObject("data").isEmpty()) { - JSONObject data = jsonResponse.getJSONObject("data"); - StringBuilder errorMsg = new StringBuilder("自定义档案同步出现错误:"); - Iterator keys = data.keySet().iterator(); - while (keys.hasNext()) { - String key = keys.next(); - errorMsg.append("\n编码 ").append(key).append(": ").append(data.get(key)); - } - throw new Exception(errorMsg.toString()); - } - } catch (Exception e) { - throw new BusinessException("调用外部接口失败:" + e.getMessage(), e); - } - } } diff --git a/mmpac/src/private/nc/bs/mmpac/pickm/bp/PickmApproveBP.java b/mmpac/src/private/nc/bs/mmpac/pickm/bp/PickmApproveBP.java new file mode 100644 index 0000000..27a63fa --- /dev/null +++ b/mmpac/src/private/nc/bs/mmpac/pickm/bp/PickmApproveBP.java @@ -0,0 +1,55 @@ +package nc.bs.mmpac.pickm.bp; + + +import nc.bs.mmpac.pickm.plugin.PickmPluginPoint; +import nc.bs.mmpac.pickm.rule.PickmApproveCheckStatusRule; +import nc.bs.mmpac.pickm.rule.PickmCheckAuditRule; +import nc.bs.mmpac.pickm.rule.PickmFbackflustimeCheckRule; +import nc.bs.mmpac.pickm.rule.PickmSetStatusRule; +import nc.bs.mmpub.rule.MMATOMaterialCheckRule; +import nc.bs.mmpub.rule.MMVOSagaFrozenValidateRule; +import nc.impl.pubapp.pattern.data.bill.template.UpdateBPTemplate; +import nc.impl.pubapp.pattern.data.bill.tool.BillTransferTool; +import nc.impl.pubapp.pattern.rule.ICompareRule; +import nc.impl.pubapp.pattern.rule.IRule; +import nc.impl.pubapp.pattern.rule.processer.CompareAroundProcesser; +import nc.util.mmf.framework.base.MMValueCheck; +import nc.vo.mmpac.pickm.entity.AggPickmVO; +import nc.vo.mmpac.pickm.enumeration.FbillstatusEnum; + +public class PickmApproveBP { + + private void addAfterRule(CompareAroundProcesser processer) { + } + + private void addBeforeRule(CompareAroundProcesser processer) { + ICompareRule pickmstatusFilterRule = new PickmApproveCheckStatusRule(true); + processer.addBeforeRule(pickmstatusFilterRule); + IRule sagasCheckrule = new MMVOSagaFrozenValidateRule(true); + processer.addBeforeRule(sagasCheckrule); + IRule pickmAuditCheckRule = new PickmCheckAuditRule(); + processer.addBeforeRule(pickmAuditCheckRule); + IRule mmatoMaterialCheckRule = new MMATOMaterialCheckRule("cmaterialvid", (String) null, "cffileid"); + processer.addBeforeRule(mmatoMaterialCheckRule); + IRule checkFbackFlusTime = new PickmFbackflustimeCheckRule(); + processer.addBeforeRule(checkFbackFlusTime); + IRule pickmSetStatusRule = new PickmSetStatusRule(FbillstatusEnum.AUDIT_STATE); + processer.addBeforeRule(pickmSetStatusRule); + } + + public AggPickmVO[] batchApprovePickm(AggPickmVO[] vos) { + if (MMValueCheck.isEmpty(vos)) { + return null; + } else { + UpdateBPTemplate bpTemplate = new UpdateBPTemplate(PickmPluginPoint.APPROVE); + BillTransferTool transTool = new BillTransferTool(vos); + this.addBeforeRule(bpTemplate.getAroundProcesser()); + this.addAfterRule(bpTemplate.getAroundProcesser()); + AggPickmVO[] fullBills = (AggPickmVO[]) transTool.getClientFullInfoBill(); + AggPickmVO[] originBills = (AggPickmVO[]) transTool.getOriginBills(); + AggPickmVO[] retBills = (AggPickmVO[]) bpTemplate.update(fullBills, originBills); + return retBills; + } + } + +} diff --git a/mmpac/src/private/nc/bs/mmpac/pickm/bp/rule/AfterApproveRuleSyncRZWMS.java b/mmpac/src/private/nc/bs/mmpac/pickm/bp/rule/AfterApproveRuleSyncRZWMS.java new file mode 100644 index 0000000..7823486 --- /dev/null +++ b/mmpac/src/private/nc/bs/mmpac/pickm/bp/rule/AfterApproveRuleSyncRZWMS.java @@ -0,0 +1,127 @@ +package nc.bs.mmpac.pickm.bp.rule; + + +import com.alibaba.fastjson.JSONArray; +import com.alibaba.fastjson.JSONObject; +import nc.bs.dao.BaseDAO; +import nc.bs.logging.Log; +import nc.bs.uapbd.util.ThirdPartyPostRequestUtil; +import nc.impl.pubapp.pattern.rule.IRule; +import nc.jdbc.framework.processor.ColumnProcessor; +import nc.pubitf.para.SysInitQuery; +import nc.vo.bd.material.MaterialVO; +import nc.vo.bd.rt.rt0004.entity.RcVO; +import nc.vo.cmp.util.StringUtils; +import nc.vo.mmpac.pickm.entity.AggPickmVO; +import nc.vo.mmpac.pickm.entity.PickmHeadVO; +import nc.vo.mmpac.pickm.entity.PickmItemVO; +import nc.vo.org.OrgVO; +import nc.vo.pub.BusinessException; +import nc.vo.pubapp.pattern.exception.ExceptionUtils; +import nc.vo.pubapp.pattern.pub.SqlBuilder; +import nc.vo.scmpub.util.ArrayUtil; + +import java.util.ArrayList; +import java.util.List; + +public class AfterApproveRuleSyncRZWMS implements IRule { + + private static Log log = Log.getInstance("rzmomlog"); + + private static BaseDAO dao = new BaseDAO(); + + @Override + public void process(AggPickmVO[] vos) { + if (ArrayUtil.isEmpty(vos)) { + return; + } + try { + // 检查并筛选领料组织 + List newAggPickmVOS = checkAndFilterBillSrcOrg(vos); + if (newAggPickmVOS.isEmpty()) { + return; + } + pushToRZMOM(newAggPickmVOS.toArray(new AggPickmVO[0])); + } catch (Exception e) { + ExceptionUtils.wrappException(e); + } + } + + private void buildSyncData(PickmHeadVO head, PickmItemVO[] bodys, JSONArray details) throws BusinessException { + for (PickmItemVO body : bodys) { + JSONObject singleObj = new JSONObject(); + String vsourcebillcode = head.getVsourcebillcode(); + String wlbm_wbid = transferCodeByPk(MaterialVO.getDefaultTableName(), MaterialVO.CODE, MaterialVO.PK_MATERIAL, body.getCbmaterialvid()); + String scgx_wbid = transferCodeByPk(RcVO.getDefaultTableName(), RcVO.VRCCODE, RcVO.CRCID, head.getVstdprocid()); + String wbid = vsourcebillcode + "_" + wlbm_wbid + "_" + scgx_wbid; + + singleObj.put("scgx_wbid", scgx_wbid); // 第三方系统使用工序id + singleObj.put("scjh_wbid", vsourcebillcode); // 第三方系统生产计划ID + singleObj.put("dwyl", body.getNplanoutastnum()); // 单位用量 + singleObj.put("djyl", body.getNplanoutastnum()); // 单据用量 + singleObj.put("clyl", body.getNplanoutastnum()); // 材料用量 + singleObj.put("wlbm_wbid", wlbm_wbid); // 第三方系统材料id + singleObj.put("wbid", wbid); // 第三方系统主键id + + details.add(singleObj); + + } + } + + private List checkAndFilterBillSrcOrg(AggPickmVO[] aggPickmVOS) throws BusinessException { + List aggvoList = new ArrayList<>(); + for (AggPickmVO aggvo : aggPickmVOS) { + String pkOrg = aggvo.getParentVO().getPk_org(); + String orgCode = transferCodeByPk(OrgVO.getDefaultTableName(), OrgVO.CODE, OrgVO.PK_ORG, pkOrg); + if ("30401".equals(orgCode)) { + aggvoList.add(aggvo); + } + } + return aggvoList; + } + + private void pushToRZMOM(AggPickmVO[] aggPickmVOS) throws BusinessException { + String rzwmsip = SysInitQuery.getParaString("GLOBLE00000000000000", "RZWMSIP"); + JSONObject jsonObject = new JSONObject(); + JSONObject data = new JSONObject(); + JSONObject dataIn = new JSONObject(); + JSONObject dataIn2 = new JSONObject(); + JSONArray details = new JSONArray(); + jsonObject.put("dataflow", "泰开BIP→RZMOMv6"); + jsonObject.put("actionCode", "cpfhtzdb"); + + for (AggPickmVO aggPickmVO : aggPickmVOS) { + PickmHeadVO head = aggPickmVO.getParentVO(); + PickmItemVO[] bodys = (PickmItemVO[]) aggPickmVO.getChildrenVO(); + buildSyncData(head, bodys, details); + } + dataIn2.put("Details", details); + dataIn.put("Data", dataIn2); + data.put("data", dataIn); + jsonObject.put("data", data); + log.error("生产BOW推送锐制请求报文:" + jsonObject.toJSONString()); + String result = ThirdPartyPostRequestUtil.sendPostRequest(rzwmsip, jsonObject.toJSONString()); + JSONObject resultObj = JSONObject.parseObject(result); + if (resultObj == null || !"true".equals(resultObj.getString("success"))) { + String errorMsg = resultObj == null ? "接口返回为空" : resultObj.getString("msg"); + throw new BusinessException("RZ同步失败,原因:" + errorMsg); + } + } + + 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(); + } + +} diff --git a/mmpac/src/private/nc/bs/mmpac/pmo/pac0002/bp/PMOApproveBP.java b/mmpac/src/private/nc/bs/mmpac/pmo/pac0002/bp/PMOApproveBP.java new file mode 100644 index 0000000..943304d --- /dev/null +++ b/mmpac/src/private/nc/bs/mmpac/pmo/pac0002/bp/PMOApproveBP.java @@ -0,0 +1,81 @@ +package nc.bs.mmpac.pmo.pac0002.bp; + +import nc.bs.mmpac.pmo.pac0002.bp.rule.AfterApprovingSynchronizeRuleRZ; +import nc.bs.mmpac.pmo.pac0002.pluginpoint.PMOPluginPoint; +import nc.bs.mmpac.pmo.pac0002.rule.*; +import nc.bs.mmpac.pmo.pac0002.rule.check.*; +import nc.bs.mmpac.pmo.pac0002.rule.fill.PMOFillApproveValueRule; +import nc.bs.mmpac.pmo.pac0002.rule.psc.PMOCreatePSCPlanRule; +import nc.bs.mmpac.pmo.pac0002.rule.psc.PMOUnApproveCheckNscNumRule; +import nc.bs.mmpub.rule.MMATOMaterialCheckRule; +import nc.bs.mmpub.rule.MMVOSagaFrozenValidateRule; +import nc.impl.pubapp.pattern.rule.ICompareRule; +import nc.impl.pubapp.pattern.rule.IRule; +import nc.impl.pubapp.pattern.rule.processer.CompareAroundProcesser; +import nc.util.mmf.framework.gc.GCUpdateBPTemplate; +import nc.vo.mmpac.pmo.pac0002.entity.PMOAggVO; + +public class PMOApproveBP { + public PMOApproveBP() { + } + + public PMOAggVO[] approve(PMOAggVO[] fullBills, PMOAggVO[] originBills) { + GCUpdateBPTemplate bp = new GCUpdateBPTemplate(PMOPluginPoint.APPROVE); + this.addApproveBeforeRule(bp.getAroundProcesser()); + this.addApproveAfterRule(bp.getAroundProcesser()); + return (PMOAggVO[]) bp.update(fullBills, originBills); + } + + private void addApproveBeforeRule(CompareAroundProcesser processer) { + IRule checkFrozenRule = new MMVOSagaFrozenValidateRule(true); + processer.addBeforeRule(checkFrozenRule); + processer.addBeforeRule(new PMOCheckApproveStatusRule()); + IRule checkDeptRule = new PMOCheckDeptNotNullRule(); + processer.addBeforeRule(checkDeptRule); + IRule approvefillvaluerule = new PMOFillApproveValueRule(false); + processer.addBeforeRule(approvefillvaluerule); + IRule approvecheckrule = new PMOCheckProcedureNotNullRule(); + processer.addBeforeRule(approvecheckrule); + IRule operTypeRule = new PMOCheckApproveOperTypeRule(); + processer.addBeforeRule(operTypeRule); + IRule mmatoMaterialCheckRule = new MMATOMaterialCheckRule((String) null, "cmaterialvid", "cffileid"); + processer.addBeforeRule(mmatoMaterialCheckRule); + } + + private void addApproveAfterRule(CompareAroundProcesser processer) { + IRule pickmrule = new PMOInsertPickmRule(); + processer.addAfterRule(pickmrule); + processer.addAfterRule(new PMOAuditAutoAuditPickmRule()); + processer.addAfterRule(new PMOCreatePSCPlanRule()); + ICompareRule auditSupplyRule = new PMOApproveAuditSupplyRule(); + processer.addAfterRule(auditSupplyRule); + // 审批后推送到RZ系统 + processer.addAfterRule(new AfterApprovingSynchronizeRuleRZ()); + } + + public PMOAggVO[] approveCancel(PMOAggVO[] fullBills, PMOAggVO[] originBills) { + GCUpdateBPTemplate bp = new GCUpdateBPTemplate(PMOPluginPoint.UNAPPROVE); + this.addApproveCancelBeforeRule(bp.getAroundProcesser()); + this.addApproveCancelAfterRule(bp.getAroundProcesser()); + return (PMOAggVO[]) bp.update(fullBills, originBills); + } + + private void addApproveCancelBeforeRule(CompareAroundProcesser processer) { + IRule checkFrozenRule = new MMVOSagaFrozenValidateRule(true); + processer.addBeforeRule(checkFrozenRule); + processer.addBeforeRule(new PMOCheckUnApproveStatusRule()); + PMOUnApproveCheckNscNumRule checkNscNumRule = new PMOUnApproveCheckNscNumRule(); + processer.addBeforeRule(checkNscNumRule); + IRule cancelcheckrule = new PMOCheckApproveCancelRule(); + processer.addBeforeRule(cancelcheckrule); + IRule cancelCheckPutPlanStatusRule = new PMOApproveCancelCheckPutPlanStatusRule(); + processer.addBeforeRule(cancelCheckPutPlanStatusRule); + IRule approvefillvaluerule = new PMOFillApproveValueRule(true); + processer.addBeforeRule(approvefillvaluerule); + } + + private void addApproveCancelAfterRule(CompareAroundProcesser processer) { + ICompareRule auditSupplyRule = new PMOApproveUnAuditSupplyRule(); + processer.addAfterRule(auditSupplyRule); + } +} diff --git a/mmpac/src/private/nc/bs/mmpac/pmo/pac0002/bp/rule/AfterApprovingSynchronizeRuleRZ.java b/mmpac/src/private/nc/bs/mmpac/pmo/pac0002/bp/rule/AfterApprovingSynchronizeRuleRZ.java new file mode 100644 index 0000000..90ae7a7 --- /dev/null +++ b/mmpac/src/private/nc/bs/mmpac/pmo/pac0002/bp/rule/AfterApprovingSynchronizeRuleRZ.java @@ -0,0 +1,160 @@ +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.logging.Log; +import nc.bs.uapbd.util.ThirdPartyPostRequestUtil; +import nc.impl.pubapp.pattern.rule.IRule; +import nc.jdbc.framework.processor.ColumnProcessor; +import nc.pubitf.para.SysInitQuery; +import nc.vo.bd.material.MaterialVO; +import nc.vo.bd.stordoc.StordocVO; +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.DeptVO; +import nc.vo.org.OrgVO; +import nc.vo.pub.BusinessException; +import nc.vo.pubapp.pattern.exception.ExceptionUtils; +import nc.vo.pubapp.pattern.pub.SqlBuilder; +import nc.vo.rum.stocks.StocksVO; +import nc.vo.scmpub.util.ArrayUtil; + +import java.util.ArrayList; +import java.util.List; + +/** + * 流程生产订单审批后推送RZ + */ +public class AfterApprovingSynchronizeRuleRZ implements IRule { + private static final Log log = Log.getInstance("rzmomlog"); + private static final BaseDAO dao = new BaseDAO(); + + @Override + public void process(PMOAggVO[] pmoAggVOS) { + if (ArrayUtil.isEmpty(pmoAggVOS)) { + return; + } + try { + // 检查并筛选生产订单 + List filteredOrders = checkAndFilterBillSrcOrg(pmoAggVOS); + if (filteredOrders.isEmpty()) { + return; + } + + // 推送到RZ系统 + pushToRZMOM(filteredOrders.toArray(new PMOAggVO[0])); + } catch (Exception e) { + log.error("同步生产订单到RZ系统失败: " + e.getMessage(), e); + ExceptionUtils.wrappException(e); + } + } + + /** + * 检查并筛选需要同步的单据 + */ + private List checkAndFilterBillSrcOrg(PMOAggVO[] pmoAggVOS) throws BusinessException { + List aggvoList = new ArrayList<>(); + for (PMOAggVO aggvo : pmoAggVOS) { + String pkOrg = aggvo.getParentVO().getPk_org(); + String orgCode = transferCodeByPk(OrgVO.getDefaultTableName(), OrgVO.CODE, OrgVO.PK_ORG, pkOrg); + if ("30401".equals(orgCode)) { + aggvoList.add(aggvo); + } + } + return aggvoList; + } + + /** + * 推送数据到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", "jhxmb"); // 生产订单的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")); + } + } + + /** + * 构建同步数据 + */ + private void buildSyncData(PMOHeadVO head, PMOItemVO[] bodys, JSONArray details) throws BusinessException { + String vbillcode = head.getVbillcode(); // 单据号 + + for (PMOItemVO body : bodys) { + JSONObject detailItem = new JSONObject(); + // 第三方系统计划类别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("sxrq", body.getTplanstarttime().toString()); + // 预计完工日期 + detailItem.put("wcrq", body.getTplanendtime().toString()); + detailItem.put("gdbj", body.getFitemstatus()); + // 计划产出数量 + detailItem.put("jhsl", body.getNmmastnum().doubleValue()); + // 入库仓库 + detailItem.put("sdck", transferCodeByPk(StordocVO.getDefaultTableName(), StordocVO.CODE, StordocVO.PK_STORDOC, body.getCinwarehouseid())); + detailItem.put("wlzdycs01", transferCodeByPk(StordocVO.getDefaultTableName(), StordocVO.CODE, StordocVO.PK_STORDOC, body.getCinwarehouseid())); + // 工作中心 生产部门ID + detailItem.put("scgc_wbid", transferCodeByPk(DeptVO.getDefaultTableName(), DeptVO.CODE, DeptVO.PK_DEPT, body.getCdeptid())); + // 订单序号 + detailItem.put("ddbh", body.getVsalebillcode()); + // 订单序号 + detailItem.put("khddh", null); + detailItem.put("ddxh", null); + // 备注说明 + detailItem.put("bzsm", body.getVnote()); + // 项目编号 + detailItem.put("htbz,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(); + } +} diff --git a/pu/src/private/nc/bs/pu/m21/action/rule/approve/AfterApprovingSynchronizeRuleRZ.java b/pu/src/private/nc/bs/pu/m21/action/rule/approve/AfterApprovingSynchronizeRuleRZ.java new file mode 100644 index 0000000..dc86323 --- /dev/null +++ b/pu/src/private/nc/bs/pu/m21/action/rule/approve/AfterApprovingSynchronizeRuleRZ.java @@ -0,0 +1,207 @@ +package nc.bs.pu.m21.action.rule.approve; + +import com.alibaba.fastjson.JSONArray; +import com.alibaba.fastjson.JSONObject; +import nc.bs.dao.BaseDAO; +import nc.bs.logging.Log; +import nc.bs.uapbd.util.ThirdPartyPostRequestUtil; +import nc.impl.pubapp.pattern.rule.IRule; +import nc.jdbc.framework.processor.ColumnProcessor; +import nc.pubitf.para.SysInitQuery; +import nc.vo.bd.material.MaterialVO; +import nc.vo.bd.psn.PsndocVO; +import nc.vo.bd.stordoc.StordocVO; +import nc.vo.bd.supplier.SupplierVO; +import nc.vo.cmp.util.StringUtils; +import nc.vo.org.OrgVO; +import nc.vo.pu.m21.entity.OrderVO; +import nc.vo.pu.m21.entity.OrderHeaderVO; +import nc.vo.pu.m21.entity.OrderItemVO; +import nc.vo.pub.BusinessException; +import nc.vo.pub.lang.UFDate; +import nc.vo.pub.lang.UFDouble; +import nc.vo.pubapp.pattern.exception.ExceptionUtils; +import nc.vo.pubapp.pattern.pub.SqlBuilder; +import nc.vo.scmpub.util.ArrayUtil; + +import java.util.ArrayList; +import java.util.List; + +import static nccloud.openapi.ic.m4c.mapping.M4cFieldsEnum.cmaterialvid; + +/** + * 采购订单审批后同步到锐制系统 + */ +public class AfterApprovingSynchronizeRuleRZ implements IRule { + + private static Log log = Log.getInstance("rzmomlog"); + private static final BaseDAO dao = new BaseDAO(); + private static final int OPERATION_ADD = 1; + private static final int STATUS_LOCKED = 1; + private static final int STATUS_ISSUED = 1; + + @Override + public void process(OrderVO[] orderVOS) { + if (ArrayUtil.isEmpty(orderVOS)) { + return; + } + try { + //检查并筛选销售出库单据为互感器公司 + List newOrderVOS = checkAndFilterBillSrcOrg(orderVOS); + if (newOrderVOS.isEmpty()) { + return; + } + // 推送到睿智系统 + pushToRZMOM(newOrderVOS.toArray(new OrderVO[0])); + } catch (Exception e) { + log.error("同步采购订单到睿智系统失败: " + e.getMessage(), e); + ExceptionUtils.wrappException(e); + } + } + + private List checkAndFilterBillSrcOrg(OrderVO[] OrderVOS) throws BusinessException { + List aggvoList = new ArrayList<>(); + for (OrderVO aggvo : OrderVOS) { + String pkOrg = aggvo.getHVO().getPk_org(); + Integer forderstatus = aggvo.getHVO().getForderstatus(); + String orgCode = transferCodeByPk(OrgVO.getDefaultTableName(), OrgVO.CODE, OrgVO.PK_ORG, pkOrg); + if ("30401".equals(orgCode)&& 3==forderstatus) { + aggvoList.add(aggvo); + } + } + return aggvoList; + } + + /** + * 推送数据到睿智MOM系统 + */ + private void pushToRZMOM(OrderVO[] orderVOS) throws BusinessException { + String rzwmsip = SysInitQuery.getParaString("GLOBLE00000000000000", "RZWMSIP"); + + JSONObject jsonObject = new JSONObject(); + // 设置请求头 + jsonObject.put("dataflow", "泰开BIP→RZMOMv6"); + jsonObject.put("actionCode", "htmxb"); + + JSONObject dataIn = new JSONObject(); + JSONObject dataIn2 = new JSONObject(); + JSONArray details = new JSONArray(); + + // 单笔/批量按明细传 + for (OrderVO orderVO : orderVOS) { + OrderHeaderVO head = orderVO.getHVO(); + OrderItemVO[] items = orderVO.getBVO(); + + // 构建同步数据 + buildSyncData(head, items, details); + } + + dataIn2.put("Details", details); + dataIn.put("Data", dataIn2); + jsonObject.put("data", dataIn); + + log.error("采购订单推送锐制请求报文:" + jsonObject.toJSONString()); + + // 使用ThirdPartyPostRequestUtil发送请求 + 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")); + } + } + + /** + * 构建同步数据 + */ + private void buildSyncData(OrderHeaderVO head, OrderItemVO[] items, JSONArray details) throws BusinessException { + if (items == null) { + return; + } + + for (OrderItemVO item : items) { + if (item == null) { + continue; + } + + JSONObject detailItem = new JSONObject(); + UFDate dbilldate = item.getDbilldate(); + // 设置订单基本信息 +// 第三方系统表体主键id + detailItem.put("htmx_wbid", item.getPk_order_b()); + //第三方系统合同ID + detailItem.put("cght_wbid", head.getVbillcode()); + //操作状态 1新增/修改、2删除(删除时只需上传wbid) + detailItem.put("operate", OPERATION_ADD); + +// detailItem.put("zbxx_cglb_wbid", null); +// detailItem.put("zbxx_cglx", DEFAULT_PURCHASE_TYPE); + + // 设置合同信息 +// 合同编号 必填 例如:采购订单编号:1001 + detailItem.put("htxsbh", head.getVbillcode()); +// 合同序号 必填 例如:采购订单序号:1、2、3 + detailItem.put("htxh", item.getCrowno()); + + // 设置物料信息 + detailItem.put("wlbm_wbid",transferCodeByPk(MaterialVO.getDefaultTableName(),MaterialVO.CODE,MaterialVO.PK_MATERIAL,item.getPk_material())); + + // 设置数量信息 + UFDouble nastnum = item.getNastnum()==null?UFDouble.ZERO_DBL:item.getNastnum(); + detailItem.put("cgsl", nastnum.getDouble()); + + //采购日期 必填 明细行的采购日期 + if (dbilldate != null) { + detailItem.put("cgrq", dbilldate.toString()); + } + // 设置供应商和采购员信息 + detailItem.put("zbxx_gycs_wbid", transferCodeByPk(SupplierVO.getDefaultTableName(),SupplierVO.CODE,SupplierVO.PK_SUPPLIER,head.getPk_supplier())); + detailItem.put("zbxx_cgy_wbid", transferCodeByPk(PsndocVO.getDefaultTableName(), PsndocVO.CODE, PsndocVO.PK_PSNDOC,head.getCemployeeid())); + + // 设置计划日期 +// 交货日期 必填 明细行的交货日期 + if (item.getDplanarrvdate() != null) { + detailItem.put("jhrq", item.getDplanarrvdate().toString()); + } + + // 设置来源单据信息 + //第三方系统采购计划id + detailItem.put("cgjh_wbid", item.getVsourcetrantype()); + //采购计划编号 + detailItem.put("cgbh", item.getVsourcecode()); + //采购计划序号 + detailItem.put("cgxh", item.getVsourcerowno()); + + // 设置仓库和备注信息 + detailItem.put("sdck",transferCodeByPk(StordocVO.getDefaultTableName(),StordocVO.CODE, StordocVO.PK_STORDOC,item.getPk_reqstordoc())); + detailItem.put("bzsm", item.getVbmemo()); + + // 设置状态信息 + detailItem.put("sdbj", STATUS_LOCKED); + detailItem.put("qfbj", STATUS_ISSUED); + + // 设置单位信息 + detailItem.put("jldw", null); + + 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(); + } +} diff --git a/pu/src/private/nc/impl/pu/m21/action/OrderApproveAction.java b/pu/src/private/nc/impl/pu/m21/action/OrderApproveAction.java new file mode 100644 index 0000000..141428f --- /dev/null +++ b/pu/src/private/nc/impl/pu/m21/action/OrderApproveAction.java @@ -0,0 +1,133 @@ +package nc.impl.pu.m21.action; + +import nc.bs.pu.m21.action.rule.approve.AfterApprovingSynchronizeRuleRZ; +import nc.bs.pu.m21.maintain.rule.SupplierFrozeChkRule; +import nc.bs.pu.m21.plugin.OrderPluginPoint; +import nc.bs.pub.compiler.AbstractCompiler2; +import nc.bs.scmpub.pf.PfParameterUtil; +import nc.bs.scmpub.rule.VOSagaFrozenValidateRule; +import nc.impl.pu.m21.action.OrderReviseApproveAction; +import nc.impl.pu.m21.action.rule.approve.*; +import nc.impl.pu.m21.action.rule.pm.OrderApprovePMSupplyRule; +import nc.impl.pu.m21.action.rule.pm.OrderRewritePMStartDateRule; +import nc.impl.pu.m21.action.rule.revise.CheckBfinalcloseRule; +import nc.impl.pubapp.pattern.data.bill.BillUpdate; +import nc.impl.pubapp.pattern.rule.processer.AroundProcesser; +import nc.itf.pu.m21.compensate.IOrderSagasCompensate; +import nc.itf.pu.reference.ic.ATPServices; +import nc.vo.pu.m21.context.OrderContext; +import nc.vo.pu.m21.entity.OrderVO; +import nc.vo.pu.pub.enumeration.POEnumBillStatus; +import nc.vo.pu.pub.rule.pf.UpdatePflowVORule; +import nc.vo.pu.pub.sagas.PUSagasOperationEnum; +import nc.vo.pub.BusinessException; +import nc.vo.pub.compiler.PfParameterVO; +import nc.vo.pub.lang.UFBoolean; +import nc.vo.pubapp.pattern.exception.ExceptionUtils; +import nc.vo.scmpub.msg.rule.UpdateMsgStatusRule; +import nc.vo.scmpub.res.billtype.POBillType; +import nc.vo.scmpub.util.AppInfoContext; +import nccloud.commons.lang.ArrayUtils; +import nccloud.pubimpl.pu.mobile.service.order.MobAfterApproveForPoOrderImpl; +import nccloud.pubitf.pu.pub.util.PuSagasUtil; + +import java.io.Serializable; +import java.util.HashMap; +import java.util.Map; + +public class OrderApproveAction { + public OrderApproveAction() { + } + + public OrderVO[] approve(OrderVO[] vos, AbstractCompiler2 script, OrderContext[] ctxs) { + Integer reviseStatus = vos[0].getHVO().getRevisionStatus(); + PfParameterUtil util = new PfParameterUtil(script == null ? null : script.getPfParameterVO(), vos); + OrderVO[] originBills = (OrderVO[]) util.getClientOrignBills(); + OrderVO[] clientBills = (OrderVO[]) util.getClientFullInfoBill(); + AroundProcesser processer = new AroundProcesser(OrderPluginPoint.APPROVE); + this.addBeforeRule(processer); + this.addAfterRule(processer, null != script ? script.getPfParameterVO() : null); + OrderVO[] customProperty = (OrderVO[]) script.getPfParameterVO().getCustomProperty("nc.bs.scmpub.pf.ORIGIN_VO_PARAMETER"); + if (customProperty == null || customProperty.length == 0) { + clientBills = vos; + } + + processer.before(clientBills); + if (null != script) { + try { + script.procFlowBacth(script.getPfParameterVO()); + } catch (Exception e) { + ExceptionUtils.wrappException(e); + } + } + + OrderVO[] returnVos; + if (reviseStatus != null && reviseStatus == 0 && vos[0].getHVO().getForderstatus() == POEnumBillStatus.APPROVE.toIntValue()) { + OrderContext ctx = ArrayUtils.isEmpty(ctxs) ? new OrderContext() : ctxs[0]; + returnVos = (new OrderReviseApproveAction()).approve(clientBills, ctx); + } else { + this.atpBeforeUpdate(clientBills); + BillUpdate update = new BillUpdate(); + returnVos = (OrderVO[]) update.update(clientBills, originBills); + + try { + AppInfoContext.setProductCode(PUSagasOperationEnum.OREDERAPPROVE.getResCommon()); + AppInfoContext.setResId(PUSagasOperationEnum.OREDERAPPROVE.getResId()); + PuSagasUtil.frozenAndAddSaga(originBills, POBillType.Order.getCode()); + Map map = new HashMap(); + map.put("opertaion", "approve"); + map.put("pk_order", originBills[0].getHVO().getPk_order()); + map.put("po_order_isrevise", UFBoolean.FALSE); + map.put("po_orderapprover", originBills[0].getHVO().getApprover()); + map.put("po_ordertaudittime", originBills[0].getHVO().getTaudittime()); + map.put("po_orderforderstatus", originBills[0].getHVO().getForderstatus()); + PuSagasUtil.compensate(IOrderSagasCompensate.class, map); + } catch (BusinessException e) { + ExceptionUtils.wrappException(e); + } + + if (vos[0].getHVO().getForderstatus() == POEnumBillStatus.APPROVE.toIntValue()) { + this.atpUpdate(returnVos); + processer.after(returnVos); + } + } + + return returnVos; + } + + private void addAfterRule(AroundProcesser processer, PfParameterVO pfParameterVO) { + processer.addAfterRule(new ApproveBudgetCtrlRule()); + processer.addAfterRule(new FilterOrderByStatusRule(POEnumBillStatus.APPROVE.toInt())); + processer.addAfterRule(new ApproveSupplyRule()); + processer.addAfterRule(new InsertStatusOnWayRule()); + processer.addAfterRule(new InsertPayPlanBillVORule()); + processer.addAfterRule(new ApproveRewritePayPlanConfirmData4CTRule()); + processer.addAfterRule(new ApproveRewritePayPlanConfirmDataRule()); + processer.addAfterRule(new FillNcaninnumRule()); + processer.addAfterRule(new ApproveAfterEventRule()); + processer.addAfterRule(new MobAfterApproveForPoOrderImpl()); + processer.addAfterFinalRule(new UpdatePflowVORule(pfParameterVO)); + processer.addAfterFinalRule(new ApproveM21AndRewriteCTPayPlan()); + processer.addAfterRule(new OrderRewritePMStartDateRule(true)); + processer.addAfterRule(new OrderApprovePMSupplyRule()); + // 采购订单审批后 同步到MES系统 + processer.addAfterRule(new AfterApprovingSynchronizeRuleRZ()); + } + + private void addBeforeRule(AroundProcesser processer) { + processer.addBeforeRule(new VOSagaFrozenValidateRule(true)); + processer.addBeforeRule(new CheckBfinalcloseRule()); + processer.addBeforeRule(new ApproveVOValidateRule()); + processer.addBeforeRule(new SupplierFrozeChkRule()); + processer.addBeforeRule(new ApproveBeforeEventRule()); + processer.addBeforeRule(new UpdateMsgStatusRule("pk_order")); + } + + private void atpBeforeUpdate(OrderVO[] vos) { + ATPServices.modifyATPBefore(POBillType.Order.getCode(), vos); + } + + private void atpUpdate(OrderVO[] vos) { + ATPServices.modifyATPAfter(POBillType.Order.getCode(), vos); + } +} diff --git a/sscivm/src/public/nc/bs/sscivm/ivsale/rule/IVApplicationCheckRule.java b/sscivm/src/public/nc/bs/sscivm/ivsale/rule/IVApplicationCheckRule.java new file mode 100644 index 0000000..6ed15e2 --- /dev/null +++ b/sscivm/src/public/nc/bs/sscivm/ivsale/rule/IVApplicationCheckRule.java @@ -0,0 +1,454 @@ +package nc.bs.sscivm.ivsale.rule; + +import nc.bs.framework.common.NCLocator; +import nc.bs.sscivm.ivsale.ivaconst.IVAWebConst; +import nc.bs.sscivm.ivsale.util.IVApplicationTspzUtil; +import nc.bs.sscivm.logger.SSCIVMLogger; +import nc.impl.pubapp.pattern.rule.IRule; +import nc.itf.sscivm.service.IVMInvoiceQueryService; +import nc.vo.pub.BusinessException; +import nc.vo.pub.VOStatus; +import nc.vo.pub.lang.UFBoolean; +import nc.vo.pub.lang.UFDouble; +import nc.vo.pubapp.pattern.exception.ExceptionUtils; +import nc.vo.sscivm.invoice.IVMInvoiceAggVO; +import nc.vo.sscivm.ivmpub.IVAplocationFPXZ; +import nc.vo.sscivm.ivmpub.IVAplocationZSFS; +import nc.vo.sscivm.ivmpub.InvoiceTypeEnum; +import nc.vo.sscivm.ivsale.IVApplicationAggVO; +import nc.vo.sscivm.ivsale.IVApplicationBodyVO; +import nc.vo.sscivm.ivsale.IVApplicationHeadVO; +import org.apache.commons.lang3.StringUtils; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + + +public class IVApplicationCheckRule implements IRule{ + @Override + public void process(IVApplicationAggVO[] vos) { + // 校验单据的购买方信息 + if(vos != null && vos.length > 0){ + for (IVApplicationAggVO aggVO : vos) { + // 增值税专用发票校验客户名称、客户纳税人识别号、地址电话、开户行及账号 + Integer fplx = aggVO.getParentVO().getFplx(); + UFBoolean sgbz = aggVO.getParentVO().getSgbz(); + if (InvoiceTypeEnum.getSpecialInvoice().contains(fplx) && (sgbz == null || !sgbz.booleanValue())) { + checkHeadNull(aggVO); + } else if (sgbz != null && sgbz.booleanValue()){//收购类申请表头判空 + checkSGHeadNull(aggVO); + } else { + // 其它类型发票客户名称不能为空 + if (isEmpty(aggVO.getParentVO().getGmf_mc())) { + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0044")/*@res "该类型的发票购买方名称不能为空"*/); + } + } + + //红冲原因校验 + checkCommonInvoice(aggVO); + + // 校验表体的必输项:项目名称、数量 + checkBodyNull(aggVO); + // 校验折扣行行号和被折扣行行号合法性 + checkBodyValid(aggVO); + //校验表头表体金额是否一致 + checkAmount(aggVO); + + if (fplx == InvoiceTypeEnum.INVOICETYPE_ZYFP_JDC.toIntValue()){ + //机动车专用发票单位校验 + checkDw(aggVO); + } + + //矿产类发票校验 + if (InvoiceTypeEnum.getKCLInvoice().contains(fplx)){ + checkKCL(aggVO); + } + + //特殊票种校验 + checkTspz(aggVO); + + } + } + } + + private void checkBodyNull(IVApplicationAggVO aggVO) throws RuntimeException { + IVApplicationBodyVO[] applicationBodyVOs = (IVApplicationBodyVO[])aggVO.getChildrenVO(); + List applicationBodyVOList = new ArrayList<>(); + + if(applicationBodyVOs != null && applicationBodyVOs.length > 0){ + for(IVApplicationBodyVO bodyvo : applicationBodyVOs){ + if(bodyvo.getStatus() != VOStatus.DELETED){ + applicationBodyVOList.add(bodyvo); + } + } + } + applicationBodyVOs = applicationBodyVOList.toArray(new IVApplicationBodyVO[0]); + IVApplicationHeadVO hvo = aggVO.getParentVO(); + Integer fplx = hvo.getFplx(); + + if (applicationBodyVOs != null && applicationBodyVOs.length > 0) { + for (IVApplicationBodyVO applicationBodyVO : applicationBodyVOs) { + if (applicationBodyVO.getXmmc() == null) { + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0047")/*@res "开票申请单表体行的物料名称不能为空!"*/); + } + + if (hvo.getSgbz() == null || !hvo.getSgbz().booleanValue() && (hvo.getHzfp() == null || !hvo.getHzfp().booleanValue()) && (hvo.getZffp() == null || !hvo.getZffp().booleanValue()) && (hvo.getCkfp() == null || !hvo.getCkfp().booleanValue())){ + if (applicationBodyVO.getPk_materiel() != null && applicationBodyVO.getTaxcode() == null) { + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0159")/*@res "开票申请单表体行的税码不能为空!"*/); + } + } + // 成品油普通发票、成品油专用发票、成品油普通发票(卷式)、增值税电子普通发票(成品油)表体数量是必输 + if (fplx == InvoiceTypeEnum.INVOICETYPE_CPYPTFP.toIntValue() + || fplx == InvoiceTypeEnum.INVOICETYPE_CPYZXFP.toIntValue() + || fplx == InvoiceTypeEnum.INVOICETYPE_CPYPTFP_JS.toIntValue() + || fplx == InvoiceTypeEnum.INVOICETYPE_DZPTFP_CPY.toIntValue()) { + if (applicationBodyVO.getXmsl() == null || applicationBodyVO.getXmsl().doubleValue() == 0.0) { + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0059")/*@res "该类型的发票表体行的数量不能为空!"*/); + } + } + } + } else { + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0099")/*@res "表体数据不能为空"*/); + } + } + + private void checkBodyValid(IVApplicationAggVO aggVO) { + IVApplicationBodyVO[] applicationBodyVOs = (IVApplicationBodyVO[])aggVO.getChildrenVO(); + List applicationBodyVOList = new ArrayList<>(); + + if(applicationBodyVOs != null && applicationBodyVOs.length > 0){ + for(IVApplicationBodyVO bodyvo : applicationBodyVOs){ + if(bodyvo.getStatus() != VOStatus.DELETED){ + applicationBodyVOList.add(bodyvo); + } + } + } + applicationBodyVOs = applicationBodyVOList.toArray(new IVApplicationBodyVO[0]); + if((null == aggVO.getParentVO().getHzfp() || UFBoolean.FALSE.equals(aggVO.getParentVO().getHzfp())) + && (null == aggVO.getParentVO().getZffp() || UFBoolean.FALSE.equals(aggVO.getParentVO().getZffp()))){ + Map rowNumAndBodyMap = new HashMap<>(); + Map rowNumAndXmmc = new HashMap<>(); + Map hhMap = new HashMap(); + for (IVApplicationBodyVO applicationBodyVO : applicationBodyVOs) { + if (applicationBodyVO.getHh() != null){ + if (hhMap.get("hh"+applicationBodyVO.getHh()) != null){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0109")/*"行号不允许重复"*/); + } else { + hhMap.put("hh"+applicationBodyVO.getHh(), "hh"+applicationBodyVO.getHh()); + } + } + if(!StringUtils.isEmpty(applicationBodyVO.getZkhhh())){ + if (applicationBodyVO.getFphxz() == null || IVAplocationFPXZ.PFPXZ_BZKH.toIntValue() != applicationBodyVO.getFphxz()){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0156")/*"当前行不是被折扣行,折扣行行号不能有值!"*/); + } + if (hhMap.get("zkhhh"+applicationBodyVO.getZkhhh()) != null){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0110")/*"折扣行行号不允许重复"*/); + } else { + hhMap.put("zkhhh"+applicationBodyVO.getZkhhh(), "zkhhh"+applicationBodyVO.getZkhhh()); + } + } + // 校验折扣行和被折扣行上的行号必输 + if (applicationBodyVO.getFphxz() !=null && IVAplocationFPXZ.PFPXZ_BZKH.toIntValue() == applicationBodyVO.getFphxz() && StringUtils.isEmpty(applicationBodyVO.getZkhhh())) { + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0097")/*@res "被折扣行的折扣行行号不能为空"*/); + } else if (applicationBodyVO.getFphxz() !=null && IVAplocationFPXZ.FPXZ_ZKH.toIntValue() == applicationBodyVO.getFphxz() && StringUtils.isEmpty(applicationBodyVO.getHh())) { + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0098")/*@res "折扣行的行号不能为空"*/); + } + // 折扣行与被折扣行金额正负校验 + if ( (applicationBodyVO.getFphxz() != null && IVAplocationFPXZ.PFPXZ_BZKH.toIntValue() == applicationBodyVO.getFphxz()) + && applicationBodyVO.getXmjshj().compareTo(UFDouble.ZERO_DBL) < 0){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0108")/*@res "蓝字开票申请被折扣行金额不能为负数"*/); + } + if ( (applicationBodyVO.getFphxz() == null || IVAplocationFPXZ.FPXZ_ZKH.toIntValue() == applicationBodyVO.getFphxz()) + && applicationBodyVO.getXmjshj().compareTo(UFDouble.ZERO_DBL) > 0){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0137")/*@res "蓝字开票申请单折扣行金额不能大于零,请修改数量为负数!"*/); + } + if (applicationBodyVO.getFphxz() !=null && IVAplocationFPXZ.FPXZ_ZKH.toIntValue() == applicationBodyVO.getFphxz()){ + rowNumAndBodyMap.put(applicationBodyVO.getHh(), applicationBodyVO); + rowNumAndXmmc.put(applicationBodyVO.getHh(), applicationBodyVO.getXmmc()); + } + } + for (IVApplicationBodyVO applicationBodyVO : applicationBodyVOs) { + if (applicationBodyVO.getFphxz() !=null && IVAplocationFPXZ.PFPXZ_BZKH.toIntValue() == applicationBodyVO.getFphxz() && !rowNumAndBodyMap.containsKey(applicationBodyVO.getZkhhh())){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0099")/*@res "折扣行与被折扣行数据校验不通过"*/); + } + } + // 校验折扣行数与被折扣行数是否一致 add by ligru 20201203 + int zkhNum = 0, bzkhNum = 0; + Map zkhMap = new HashMap(); + for (IVApplicationBodyVO applicationBodyVO : applicationBodyVOs) { + if (applicationBodyVO.getFphxz() !=null && IVAplocationFPXZ.PFPXZ_BZKH.toIntValue() == applicationBodyVO.getFphxz()){ + bzkhNum++; + } else if(applicationBodyVO.getFphxz() !=null && IVAplocationFPXZ.FPXZ_ZKH.toIntValue() == applicationBodyVO.getFphxz()){ + zkhMap.put(applicationBodyVO.getHh(), applicationBodyVO); + zkhNum++; + } + } + if(zkhNum != bzkhNum){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0099")/*@res "折扣行与被折扣行数据校验不通过"*/); + } + // 校验折扣行与被折扣行项目名称是否相同 + for (IVApplicationBodyVO applicationBodyVO : applicationBodyVOs) { + if (applicationBodyVO.getFphxz() != null + && IVAplocationFPXZ.PFPXZ_BZKH.toIntValue() == applicationBodyVO.getFphxz() + && !java.util.Objects.equals(rowNumAndXmmc.get(applicationBodyVO.getZkhhh()), applicationBodyVO.getXmmc())) + { + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID( + "1058sal_0", + "01058sal-0116", + null, + new String[] { rowNumAndXmmc.get(applicationBodyVO.getZkhhh()), applicationBodyVO.getXmmc() }/*@res 折扣行项目名称[{0}]与被折扣行项目名称[{1}]不一致*/)); + } + + if(applicationBodyVO.getFphxz() != null + && IVAplocationFPXZ.PFPXZ_BZKH.toIntValue() == applicationBodyVO.getFphxz() + && applicationBodyVO.getXmjshj().add(zkhMap.get(applicationBodyVO.getZkhhh()).getXmjshj()).doubleValue() <0){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", "01058sal-0120")/*"被折扣行的金额应大于折扣行金额!"*/); + } + } + } + } + + private void checkSGHeadNull(IVApplicationAggVO aggVO) throws RuntimeException{ + if(isEmpty(aggVO.getParentVO().getXsf_mc())){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0193")/*@res "收购发票销售方名称不能为空"*/); + } + if(isEmpty(aggVO.getParentVO().getXsf_nsrsbh())){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0194")/*@res "收购发票销售方纳税人识别号不能为空"*/); + } + } + + private void checkHeadNull(IVApplicationAggVO aggVO) throws RuntimeException { + if(isEmpty(aggVO.getParentVO().getGmf_mc())){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0040")/*@res "增值税专用发票购买方名称不能为空"*/); + } + + if(isEmpty(aggVO.getParentVO().getGmf_nsrsbh())){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0041")/*@res "增值税专用发票购买方纳税人识别号不能为空"*/); + } + //全电专票无需校验地址电话银行账号 + if(aggVO.getHeadVO().getFplx() == InvoiceTypeEnum.DZFP_ZZSZYFP.toIntValue() || aggVO.getHeadVO().getFplx() == InvoiceTypeEnum.ZZFP_ZZSZYFP.toIntValue() + || aggVO.getHeadVO().getFplx() == InvoiceTypeEnum.ZZFP_SDFP.toIntValue()){ + return; + } + if(isEmpty(aggVO.getParentVO().getGmf_dzdh())){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0042")/*@res "增值税专用发票购买方地址电话不能为空"*/); + } + + if(isEmpty(aggVO.getParentVO().getGmf_yhzh())){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0043")/*@res "增值税专用发票购买方银行账号不能为空"*/); + } + + } + + private void checkCommonInvoice(IVApplicationAggVO aggVO) throws RuntimeException { + + //普票红字申请红冲原因不能为空,专票红字信息申请表不能为空@税率说明红冲原因@ + if (aggVO.getHeadVO().getHzfp() != null && aggVO.getHeadVO().getHzfp().booleanValue()){ + if ((InvoiceTypeEnum.getCommonInvoice().contains(aggVO.getHeadVO().getFplx()) || InvoiceTypeEnum.DZFP_ZZSZYFP.toIntValue()==aggVO.getHeadVO().getFplx())){ + if (isEmpty(aggVO.getParentVO().getHcyy())){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0185")/*"红冲原因不能为空"*/); + } + + IVApplicationBodyVO[] applicationBodyVOs = (IVApplicationBodyVO[])aggVO.getChildrenVO(); + for (IVApplicationBodyVO applicationBodyVO : applicationBodyVOs){ + //不校验删除行 + if (applicationBodyVO.getStatus() == VOStatus.DELETED){ + continue; + } + if (applicationBodyVO.getSpbm() != null){ + //税收编码为以1、2开头的冲红原因不允许选择“服务中止”; + if ((applicationBodyVO.getSpbm().startsWith("1") ||applicationBodyVO.getSpbm().startsWith("2")) && aggVO.getParentVO().getHcyy().equals("3")){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0186")/*"当前税收编码的红冲原因不允许选择:服务中止"*/); + } + //税收编码为以3开头的冲红原因不允许选择“销售退回” + if (applicationBodyVO.getSpbm().startsWith("3") && aggVO.getParentVO().getHcyy().equals("1")){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0187")/*"当前税收编码的红冲原因不允许选择:销货退回"*/); + } + } + } + + //红冲金额与蓝字发票金额一致时,红冲原因不允许选择“销售折让” + String condition = "fpdm='"+aggVO.getHeadVO().getFpdm()+"' and fphm='"+aggVO.getHeadVO().getFphm()+"' and dr = 0 and (billtypecode = 'SSIV-Cxx-sale' or (billtypecode = 'SSIV-Cxx-rec' and invoice_type in (109,309) )) "; + if (aggVO.getHeadVO().getFpdm() == null){ + condition = " fphm='"+aggVO.getHeadVO().getFphm()+"' and dr = 0 and (billtypecode = 'SSIV-Cxx-sale' or (billtypecode = 'SSIV-Cxx-rec' and invoice_type in (109,309) )) "; + } + try { + IVMInvoiceAggVO[] vos = NCLocator.getInstance().lookup(IVMInvoiceQueryService.class).queryAggVOsByCondition(condition); + if (vos != null){ + if ((vos[0].getHeadVO().getJshj().add(aggVO.getHeadVO().getJshj())).compareTo(UFDouble.ZERO_DBL) == 0 && aggVO.getParentVO().getHcyy().equals("4")){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0188")/*"全部红冲的原因不允许选择:销售折让"*/); + } + } + } catch (BusinessException e) { + SSCIVMLogger.error(e.getMessage(), e); + throw new RuntimeException(e); + } + + } + + if (InvoiceTypeEnum.getSpecialInvoice().contains(aggVO.getHeadVO().getFplx()) && aggVO.getHeadVO().getFplx() != InvoiceTypeEnum.DZFP_ZZSZYFP.toIntValue() && isEmpty(aggVO.getParentVO().getHzxxsqb())){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0189")/*"红字信息申请表不能为空"*/); + } + } + } + + /** + * 校验表头表体金额是否一致 + * @param aggVO + */ + private void checkAmount(IVApplicationAggVO aggVO) { + UFDouble jshj = UFDouble.ZERO_DBL; + UFDouble hjje = UFDouble.ZERO_DBL; + UFDouble hjse = UFDouble.ZERO_DBL; + + //表体金额合计 + for (IVApplicationBodyVO bodyvo : aggVO.getBodyVOs()){ + if (bodyvo.getStatus() == VOStatus.DELETED){ + continue; + } + jshj = jshj.add(bodyvo.getXmjshj() == null ? UFDouble.ZERO_DBL : bodyvo.getXmjshj()); + hjje = hjje.add(bodyvo.getXmje() == null ? UFDouble.ZERO_DBL : bodyvo.getXmje()); + hjse = hjse.add(bodyvo.getSe() == null ? UFDouble.ZERO_DBL : bodyvo.getSe()); + } + + IVApplicationHeadVO headvo = aggVO.getHeadVO(); + //价税合计判断 + if (headvo.getJshj().compareTo(jshj) != 0){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0160")/*"表头表体价税合计不一致!"*/); + } + //无税金额判断 + if (headvo.getHjje().compareTo(hjje) != 0){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0161")/*"表头表体无税金额不一致!"*/); + } + //无税金额判断 + if (headvo.getHjse().compareTo(hjse) != 0){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0162")/*"表头表体税额不一致!"*/); + } + } + + /** + * 校验机动车专用发票单位 + * @param aggVO + */ + private void checkDw(IVApplicationAggVO aggVO){ + for (IVApplicationBodyVO body : aggVO.getBodyVOs()){ + if (body == null || !nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0","01058sal-0225")/*@res "辆"*/.equals(body.getDw())){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0155", null, new String[] {nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0","01058sal-0225")/*@res "辆"*/})/*"增值税专用发票(机动车)单位必须为辆,请修改!"*/); + } + } + } + + /** + * 矿产类发票校验 + * @param aggVO 开票申请VO + */ + private void checkKCL(IVApplicationAggVO aggVO){ + for (IVApplicationBodyVO body : aggVO.getBodyVOs()){ + //不校验删除行 + if (body.getStatus() == VOStatus.DELETED){ + continue; + } + //计量单位校验 + if(body.getDw() == null || (!nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0","01058sal-0226")/*@res "立方米"*/.equals(body.getDw()) && !nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0","01058sal-0227")/*@res "吨"*/.equals(body.getDw()) && !nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0","01058sal-0228")/*@res "千克"*/.equals(body.getDw()) && !nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0","01058sal-0229")/*@res "克"*/.equals(body.getDw())&& !nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0","01058sal-0230")/*@res "克拉"*/.equals(body.getDw()))){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0190", null, new String[]{nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0","01058sal-0231")/*@res "立方米、吨、千克、克、克拉"*/})/*"矿产类发票计量单位必须为:立方米、吨、千克、克、克拉!"*/); + } + //数量单价校验 + if (body.getXmsl() == null || body.getXmsl().compareTo(UFDouble.ZERO_DBL) == 0 || body.getXmdj() == null || body.getXmdj().compareTo(UFDouble.ZERO_DBL) == 0){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0191")/*"矿产类发票单价数量不能为空!"*/); + } + //税收分类编码不为空时,需校验:税编为102矿产品开头且非102040303稀土矿产品开头的商品。 + //税收分类编码为空且物料为空,“商品编码”字段含义为税收分类编码,此时需校验:税编为102矿产品开头且非102040303稀土矿产品开头的商品 + if ((!StringUtils.isEmpty(body.getSsflbm()) && (!body.getSsflbm().startsWith("102") || body.getSsflbm().startsWith("102040303"))) + ||(StringUtils.isEmpty(body.getSsflbm()) && StringUtils.isEmpty(body.getPk_materiel()) &&(StringUtils.isEmpty(body.getSpbm()) || !body.getSpbm().startsWith("102") || body.getSpbm().startsWith("102040303")))){ + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0192", null, new String[]{"102", "102040303"})/*"矿产类发票税收分类编码必须为102矿产品开头且非102040303稀土矿产品开头的商品!"*/); + } + } + } + + + public void checkTspz(IVApplicationAggVO aggVO) { + + String tspz = aggVO.getParentVO().getTspz() == null ? null : IVApplicationTspzUtil.getTspzCode( aggVO.getParentVO().getTspz()); + //数电特殊票种为E06不动产租赁、E05不动产销售、E03建筑服务时,或为差额开票时,发票明细表体行只允许一正常明细行,或一组折扣与被折扣行 + String zsfs = aggVO.getParentVO().getZsfs(); + if(IVAWebConst.TSPZ_JZFW.equals(tspz)|| + IVAWebConst.TSPZ_BDCXS.equals(tspz) || + IVAWebConst.TSPZ_BDCZN.equals(tspz) || + String.valueOf(IVAplocationZSFS.HCYY_CEZS.toIntValue()).equals(zsfs) + ) { + //判断表体是否满足条件 + boolean bodyflag = false; + IVApplicationBodyVO[] bodys = aggVO.getBodyVOs(); + //过滤已删除的表体 + List unDelBodys = new ArrayList<>(); + for (IVApplicationBodyVO body : bodys){ + if (body.getStatus() != VOStatus.DELETED){ + unDelBodys.add(body); + } + } + bodys = unDelBodys.toArray(new IVApplicationBodyVO[0]); + if(bodys!=null && bodys.length>2) { + bodyflag =true; + }else if(bodys!=null && bodys.length==2){ + for(IVApplicationBodyVO body:bodys) { + int fphxz = body.getFphxz(); + //判断是否折扣及被折扣 + if(IVAplocationFPXZ.FPXZ_ZKH.toIntValue()!= fphxz && IVAplocationFPXZ.PFPXZ_BZKH.toIntValue()!=fphxz) { + bodyflag = true; + } + } + } + if(bodyflag) { + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0263")/*@res "该票种属于特定业务或差额开票,开具时不可多行开具!"*/); + } + } + + if( IVAWebConst.TSPZ_BDCXS.equals(tspz) || IVAWebConst.TSPZ_BDCZN.equals(tspz)) { + String bdcdz = aggVO.getParentVO().getBdcdz(); + if (bdcdz == null ||(!bdcdz.contains("街") && !bdcdz.contains("路") && !bdcdz.contains("村") && !bdcdz.contains("乡") && !bdcdz.contains("镇")&& !bdcdz.contains("道") && !bdcdz.contains("巷") && !bdcdz.contains("号"))) { + ExceptionUtils.wrappBusinessException(nc.vo.ml.NCLangRes4VoTransl.getNCLangRes().getStrByID("1058sal_0", + "01058sal-0265")/*@res "不动产地址必须包含街、路、村、乡、 镇、道、巷、号等任意一个关键词"*/); + } + } + + } + public boolean isEmpty(String str) { + return StringUtils.isBlank(str) || "null".equals(str); + } + +} diff --git a/uapbd/src/public/nc/bs/uapbd/util/ThirdPartyPostRequestUtil.java b/uapbd/src/public/nc/bs/uapbd/util/ThirdPartyPostRequestUtil.java new file mode 100644 index 0000000..0828fe3 --- /dev/null +++ b/uapbd/src/public/nc/bs/uapbd/util/ThirdPartyPostRequestUtil.java @@ -0,0 +1,68 @@ +package nc.bs.uapbd.util; + + +import nc.vo.pub.BusinessException; + +import java.io.BufferedReader; +import java.io.InputStreamReader; +import java.io.OutputStream; +import java.net.HttpURLConnection; +import java.net.URL; +/** + * @Classname ThirdPartyPostRequestUtil + * @Description TODO + * @Version 1.0.0 + * @Date 2025/5/15 18:22 + * @Created by ame + */ +public class ThirdPartyPostRequestUtil { + + private static final int DEFAULT_CONNECT_TIMEOUT = 10000; + private static final int DEFAULT_READ_TIMEOUT = 10000; + + /** + * 向第三方系统发送 POST 请求,并根据 HTTP 状态码返回数据 + * + * @param requestUrl 请求地址 + * @param requestBody 请求体(JSON 格式) + * @return 如果响应码为 200,则返回响应内容;否则返回错误信息 + */ + public static String sendPostRequest(String requestUrl, String requestBody) throws BusinessException { + try { + URL url = new URL(requestUrl); + HttpURLConnection connection = (HttpURLConnection) url.openConnection(); + + // 设置请求方法和参数 + connection.setRequestMethod("POST"); + connection.setDoOutput(true); // 允许输出 + connection.setConnectTimeout(DEFAULT_CONNECT_TIMEOUT); // 设置连接超时时间 + connection.setReadTimeout(DEFAULT_READ_TIMEOUT); // 设置读取超时时间 + connection.setRequestProperty("Content-Type", "application/json"); // 设置请求头 + + // 发送请求体 + try (OutputStream os = connection.getOutputStream()) { + byte[] input = requestBody.getBytes("utf-8"); + os.write(input, 0, input.length); + } + + // 获取响应 + int responseCode = connection.getResponseCode(); + + if (responseCode == HttpURLConnection.HTTP_OK) { // 成功响应 + BufferedReader in = new BufferedReader(new InputStreamReader(connection.getInputStream())); + String line; + StringBuilder responseBuilder = new StringBuilder(); + while ((line = in.readLine()) != null) { + responseBuilder.append(line); + } + in.close(); + return responseBuilder.toString(); // 返回成功响应数据 + } else { + throw new BusinessException("POST 请求失败,响应码:" + responseCode) ; // 返回失败信息 + } + } catch (Exception e) { + throw new BusinessException("发生异常:" + e.getMessage()) ; // 异常处理 + } + } + +}