diff --git a/emis-biz/src/main/java/com/xdadan/erp/emis/domain/EmisSettlePayRecord.java b/emis-biz/src/main/java/com/xdadan/erp/emis/domain/EmisSettlePayRecord.java index 0e2f18c87..4df94bf88 100644 --- a/emis-biz/src/main/java/com/xdadan/erp/emis/domain/EmisSettlePayRecord.java +++ b/emis-biz/src/main/java/com/xdadan/erp/emis/domain/EmisSettlePayRecord.java @@ -42,6 +42,8 @@ public class EmisSettlePayRecord extends BaseEntity private Long id; /* 支付序号 */ private String payId; + /* 销账申请编号,关联的销账申请编号 */ + private String writeoffApplyNo; /* 收款来源 1-微信支付2支付宝 3-对公 */ private String payType; /* 收付类型 1-收款 2-退款 */ diff --git a/emis-biz/src/main/java/com/xdadan/erp/emis/domain/EmisWriteoffApply.java b/emis-biz/src/main/java/com/xdadan/erp/emis/domain/EmisWriteoffApply.java index 973312351..24de92fff 100644 --- a/emis-biz/src/main/java/com/xdadan/erp/emis/domain/EmisWriteoffApply.java +++ b/emis-biz/src/main/java/com/xdadan/erp/emis/domain/EmisWriteoffApply.java @@ -91,6 +91,10 @@ public class EmisWriteoffApply extends BaseEntity { @Excel(name = "申请说明") private String applyMemo; + /* 收款记录支付ID,财务中心审核通过后关联的收款记录ID */ + @Excel(name = "收款记录ID") + private String payId; + /* 中心审核状态 0-未审核 1-审核通过 2-审核拒绝 3-已撤销 */ @Excel(name = "中心审核状态") private String blCenterConfirmed; diff --git a/emis-biz/src/main/java/com/xdadan/erp/emis/mapper/EmisSettlePayRecordMapper.java b/emis-biz/src/main/java/com/xdadan/erp/emis/mapper/EmisSettlePayRecordMapper.java index 63a0b1e79..201087adb 100644 --- a/emis-biz/src/main/java/com/xdadan/erp/emis/mapper/EmisSettlePayRecordMapper.java +++ b/emis-biz/src/main/java/com/xdadan/erp/emis/mapper/EmisSettlePayRecordMapper.java @@ -30,7 +30,7 @@ import org.apache.ibatis.annotations.Param; public interface EmisSettlePayRecordMapper extends BaseMapper { /** * 主键查询 - * + * * @param id * @return */ @@ -92,6 +92,14 @@ public interface EmisSettlePayRecordMapper extends BaseMapper 0) { - // throw new EmisBizError("运单号 " + detail.getBillCode() + " 的申请金额(" + - // detail.getApplyMoney() + ") + 已收金额(" + receivedAmount + ") = " + - // totalAmount + " 超过运单应收金额(" + detail.getEmisWaybill().getFreight() + ")"); - // } + if (totalAmount.compareTo(recMoney) > 0) { + throw new EmisBizError("运单号 " + detail.getBillCode() + " 的申请金额(" + detail.getApplyMoney() + + ") + 已收金额(" + receivedAmount + ") = " + totalAmount + " 超过账单应收金额(" + + recMoney + ")"); + } } // 验证总销账金额 @@ -355,12 +373,16 @@ public class EmisWriteoffApplyServiceImpl extends EmisBaseService implements IEm // 更新相关开票记录的收款金额和付款状态 updateInvoiceRecordPaymentStatus(existingApply, detailList, true); + // 创建收款记录 + String payId = createSettlePayRecord(existingApply, detailList); + // 所有业务数据更新成功后,再更新审核状态 SysUser currentUser = SecurityUtils.getLoginUser().getUser(); emisWriteoffApply.setBlCenterConfirmed(WriteoffApplyStatus.CENTER_APPROVED.statusCode); emisWriteoffApply.setCenterConfirmManCode(currentUser.getEmpCode()); emisWriteoffApply.setCenterConfirmManName(currentUser.getEmpName()); emisWriteoffApply.setCenterConfirmDate(new Date()); + emisWriteoffApply.setPayId(payId); // 保存收款记录支付ID // 更新申请状态 int result = emisWriteoffApplyMapper.auditCenterPass(emisWriteoffApply); @@ -500,6 +522,9 @@ public class EmisWriteoffApplyServiceImpl extends EmisBaseService implements IEm // 更新相关开票记录的收款金额和付款状态(回退) updateInvoiceRecordPaymentStatus(existingApply, detailList, false); + // 删除收款记录 + deleteSettlePayRecord(existingApply); + // 所有业务数据回退成功后,再更新审核状态 SysUser currentUser = SecurityUtils.getLoginUser().getUser(); emisWriteoffApply.setBlHeadquartersConfirmed(WriteoffApplyStatus.HEADQUARTERS_REJECTED.statusCode); @@ -1189,7 +1214,7 @@ public class EmisWriteoffApplyServiceImpl extends EmisBaseService implements IEm log.info("销账申请通知发送成功,申请编号:{},操作类型:{}", apply.getApplyNo(), actionType); } catch (Exception e) { - log.error("发送销账申请通知失败,申请编号:{},操作类型:{}", apply.getApplyNo(), actionType, e); + log.error("发送销账申请通知失败,申请编号:{},操作类型:{}", (apply != null ? apply.getApplyNo() : null), actionType, e); } } @@ -1401,4 +1426,173 @@ public class EmisWriteoffApplyServiceImpl extends EmisBaseService implements IEm // 不抛出异常,避免影响主流程 } } + + /** + * 创建收款记录 + * 参考EmisSettlePayRecordServiceImpl.insertEmisSettlePayRecord逻辑 + * 创建收款记录及其关联关系 + * 一个支付ID对应一条收款记录,多个结算账单号用逗号分隔 + * + * @param apply 销账申请 + * @param detailList 申请明细列表 + * @return 生成的支付ID + */ + private String createSettlePayRecord(EmisWriteoffApply apply, List detailList) + throws EmisBizError { + try { + log.info("开始创建收款记录,申请ID: {}", apply.getId()); + + if (CollectionUtils.isEmpty(detailList)) { + log.warn("申请明细为空,无法创建收款记录,申请ID: {}", apply.getId()); + return null; + } + + // 收集所有结算账单号(去重) + Set settleBillNoSet = detailList.stream() + .filter(detail -> StringUtil.isNotBlank(detail.getSettleBillNo())) + .map(EmisWriteoffApplyDetail::getSettleBillNo) + .collect(java.util.stream.Collectors.toSet()); + + if (settleBillNoSet.isEmpty()) { + log.warn("没有有效的结算账单号,无法创建收款记录,申请ID: {}", apply.getId()); + return null; + } + + // 计算总申请金额 + BigDecimal totalApplyMoney = detailList.stream() + .map(EmisWriteoffApplyDetail::getApplyMoney) + .filter(Objects::nonNull) + .reduce(BigDecimal.ZERO, BigDecimal::add); + + // 将结算账单号用逗号连接 + String settleBillNos = String.join(",", settleBillNoSet); + + // 创建收款记录(一个支付ID对应一条记录) + String payId = createPayRecordForApply(apply, settleBillNos, totalApplyMoney, detailList); + + log.info("收款记录创建完成,申请ID: {}, 支付ID: {}, 结算账单号: {}, 总金额: {}", + apply.getId(), payId, settleBillNos, totalApplyMoney); + + return payId; + } catch (Exception e) { + log.error("创建收款记录失败,申请ID: {}", apply.getId(), e); + throw new EmisBizError("创建收款记录失败:" + e.getMessage()); + } + } + + /** + * 为销账申请创建收款记录 + * 一个支付ID对应一条收款记录,多个结算账单号用逗号分隔 + * + * @param apply 销账申请 + * @param settleBillNos 结算账单号(多个用逗号分隔) + * @param totalApplyMoney 总申请金额 + * @param detailList 申请明细列表 + * @return 生成的支付ID + */ + private String createPayRecordForApply(EmisWriteoffApply apply, String settleBillNos, + BigDecimal totalApplyMoney, List detailList) throws EmisBizError { + try { + // 生成支付ID + String payId = WaybillHelper.genPayId(); + + // 获取当前用户信息 + SysUser currentUser = SecurityUtils.getLoginUser().getUser(); + + // 创建收款记录主表 + EmisSettlePayRecord payRecord = new EmisSettlePayRecord(); + payRecord.setPayId(payId); + payRecord.setWriteoffApplyNo(apply.getApplyNo()); // 设置销账申请编号 + payRecord.setPayType("7"); // 销账收款类型 + payRecord.setRecType("1"); // 收款类型 + payRecord.setPayMan(apply.getApplyManName()); + payRecord.setPayManCode(apply.getApplyManCode()); + payRecord.setSettleBillNo(settleBillNos); // 多个账单号用逗号分隔 + payRecord.setBlAudit("1"); // 已审核 + payRecord.setAuditDate(new Date()); + payRecord.setAuditManCode(currentUser.getEmpCode()); + payRecord.setAuditSiteCode(currentUser.getDeptId().toString()); + + // 设置客户信息(从第一个明细中获取) + if (!detailList.isEmpty() && detailList.get(0).getEmisWaybill() != null) { + EmisWaybill waybill = detailList.get(0).getEmisWaybill(); + payRecord.setCustomerCode(waybill.getCustomerCode()); + payRecord.setCustomerName(waybill.getCustomerName()); + } + + payRecord.setPayMoney(totalApplyMoney); + payRecord.setPayStatus("2"); // 支付成功 + payRecord.setPayStatusDesc("销账收款成功"); + payRecord.setSettleType("1"); // 现金结算 + payRecord.setTradeDate(new Date()); + payRecord.setRecManCode(currentUser.getEmpCode()); + + // 插入收款记录主表 + emisSettlePayRecordMapper.insertEmisSettlePayRecord(payRecord); + + // 创建收款账单关联关系(为每个结算账单创建关联) + String[] settleBillNoArray = settleBillNos.split(","); + for (String settleBillNo : settleBillNoArray) { + if (StringUtil.isNotBlank(settleBillNo.trim())) { + EmisSettlePayBillRel payBillRel = new EmisSettlePayBillRel(); + payBillRel.setPayId(payId); + payBillRel.setSettleBillNo(settleBillNo.trim()); + emisSettlePayBillRelMapper.insertEmisSettlePayBillRel(payBillRel); + } + } + + // 创建收款运单关联关系 + for (EmisWriteoffApplyDetail detail : detailList) { + if (StringUtil.isNotBlank(detail.getBillCode())) { + EmisSettlePayRel payRel = new EmisSettlePayRel(); + payRel.setPayId(payId); + payRel.setBillNo(detail.getBillCode()); + payRel.setPayMoney(detail.getApplyMoney()); + emisSettlePayRelMapper.insertEmisSettlePayRel(payRel); + } + } + + log.info("销账申请收款记录创建成功,申请ID: {}, 支付ID: {}, 结算账单号: {}, 总金额: {}", + apply.getId(), payId, settleBillNos, totalApplyMoney); + + return payId; + } catch (Exception e) { + log.error("创建销账申请收款记录失败,申请ID: {}", apply.getId(), e); + throw new EmisBizError("创建销账申请收款记录失败:" + e.getMessage()); + } + } + + /** + * 删除收款记录 + * 删除销账申请对应的收款记录及其关联关系 + * 根据payId精确软删除对应的收款记录 + * + * @param apply 销账申请 + */ + private void deleteSettlePayRecord(EmisWriteoffApply apply) throws EmisBizError { + try { + log.info("开始删除收款记录,申请ID: {}, payId: {}", apply.getId(), apply.getPayId()); + + // 如果没有payId,则无法删除收款记录 + if (StringUtil.isBlank(apply.getPayId())) { + log.warn("申请没有关联的payId,无法删除收款记录,申请ID: {}", apply.getId()); + return; + } + + // 根据payId软删除收款记录主表 + int deleteCount = emisSettlePayRecordMapper.deleteEmisSettlePayRecordByPayId(apply.getPayId()); + + if (deleteCount > 0) { + log.info("收款记录软删除成功,支付ID: {}, 删除记录数: {}", apply.getPayId(), deleteCount); + } else { + log.warn("未找到对应的收款记录进行删除,支付ID: {}", apply.getPayId()); + } + + log.info("收款记录删除完成,申请ID: {}, payId: {}", apply.getId(), apply.getPayId()); + } catch (Exception e) { + log.error("删除收款记录失败,申请ID: {}", apply.getId(), e); + throw new EmisBizError("删除收款记录失败:" + e.getMessage()); + } + } + } diff --git a/emis-biz/src/main/resources/mapper/EmisSettlePayRecordMapper.xml b/emis-biz/src/main/resources/mapper/EmisSettlePayRecordMapper.xml index 4307ba44b..27275f133 100644 --- a/emis-biz/src/main/resources/mapper/EmisSettlePayRecordMapper.xml +++ b/emis-biz/src/main/resources/mapper/EmisSettlePayRecordMapper.xml @@ -7,6 +7,7 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" + @@ -87,7 +88,7 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" select - a.id, a.pay_id, a.pay_type, a.rec_type, a.pay_man, a.pay_man_code, a.settle_bill_no, + a.id, a.pay_id, a.writeoff_apply_no, a.pay_type, a.rec_type, a.pay_man, a.pay_man_code, a.settle_bill_no, a.bl_audit, a.audit_date, a.audit_man_code, a.audit_site_code, a.customer_code, a.customer_name, a.pay_money, a.pay_status, a.pay_status_desc, a.break_type, a.break_reason, a.break_emp_code, a.rec_man_code, a.settle_type, a.refund_date, @@ -302,7 +303,7 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" @@ -441,6 +442,7 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" id, pay_id, + writeoff_apply_no, pay_type, rec_type, pay_man, @@ -491,6 +493,7 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" #{id}, #{payId}, + #{writeoffApplyNo}, #{payType}, #{recType}, #{payMan}, @@ -544,6 +547,7 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" update emis_settle_pay_record pay_id = #{payId}, + writeoff_apply_no = #{writeoffApplyNo}, pay_type = #{payType}, rec_type = #{recType}, pay_man = #{payMan}, @@ -605,6 +609,10 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" + + update emis_settle_pay_record set del_flag='1' where pay_id = #{payId} + + select distinct wa.id, wa.apply_no, wa.apply_man_code, wa.apply_man_name, wa.apply_site_code, wa.apply_site_name, - wa.apply_date, wa.writeoff_amount, wa.pay_type, wa.trade_date, wa.recipient, wa.apply_memo, + wa.apply_date, wa.writeoff_amount, wa.pay_type, wa.trade_date, wa.recipient, wa.apply_memo, wa.pay_id, wa.bl_center_confirmed, wa.center_confirm_man_code, wa.center_confirm_man_name, wa.center_confirm_date, wa.center_confirm_note, wa.center_reject_reason, wa.bl_headquarters_confirmed, wa.headquarters_confirm_man_code, wa.headquarters_confirm_man_name, wa.headquarters_confirm_date, wa.headquarters_confirm_note, @@ -126,6 +127,7 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" trade_date, recipient, apply_memo, + pay_id, bl_center_confirmed, center_confirm_man_code, center_confirm_man_name, @@ -161,6 +163,7 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" #{tradeDate}, #{recipient}, #{applyMemo}, + #{payId}, #{blCenterConfirmed}, #{centerConfirmManCode}, #{centerConfirmManName}, @@ -197,6 +200,7 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" apply_date = #{applyDate}, writeoff_amount = #{writeoffAmount}, apply_memo = #{applyMemo}, + pay_id = #{payId}, bl_center_confirmed = #{blCenterConfirmed}, center_confirm_man_code = #{centerConfirmManCode}, center_confirm_man_name = #{centerConfirmManName}, @@ -240,6 +244,7 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" center_confirm_man_name = #{centerConfirmManName}, center_confirm_date = #{centerConfirmDate}, center_confirm_note = #{centerConfirmNote}, + pay_id = #{payId}, update_by = #{updateBy}, update_time = #{updateTime} where id = #{id}