fix: 开票申请与正式结算单同步金蝶入口增加行锁互斥
- doSyncKingdee 首行改为 lockedExisting 行锁读(FOR UPDATE),审批自动推/手动按钮/定时重推三入口在同一单据上串行化 - 后到请求等锁后读到已提交状态,命中已同步幂等分支直接返回金蝶单号 - 修复并发推送触发金蝶「已提交状态下的单据不允许修改」的假失败与重复建单风险
This commit is contained in:
+9
-1
@@ -981,7 +981,7 @@ public class FormalSettlementServiceImpl extends BaseServiceImpl<FormalSettlemen
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public String doSyncKingdee(Long id) {
|
||||
FormalSettlement settlement = existing(id);
|
||||
FormalSettlement settlement = lockedExisting(id);
|
||||
if (!TransportBusiConstant.APPROVED.equals(settlement.getApprovalStatus())) throw new ServiceException("仅审批通过的正式结算单允许同步金蝶");
|
||||
// 已同步幂等返回(含历史由付款申请同步联动回写的存量已同步数据);星瀚内码由附件补传分支反查回填
|
||||
if ("synced".equals(settlement.getKingdeeSyncStatus())) return settlement.getKingdeeBillNo();
|
||||
@@ -2325,6 +2325,14 @@ public class FormalSettlementServiceImpl extends BaseServiceImpl<FormalSettlemen
|
||||
return entity;
|
||||
}
|
||||
|
||||
/** 行锁读:同一单据并发推送串行化(锁随 doSyncKingdee 事务提交释放,后者读到已同步状态幂等返回) */
|
||||
private FormalSettlement lockedExisting(Long id) {
|
||||
FormalSettlement entity = baseMapper.selectOne(Wrappers.<FormalSettlement>lambdaQuery()
|
||||
.eq(FormalSettlement::getId, id).last("FOR UPDATE"));
|
||||
if (entity == null || Objects.equals(entity.getIsDeleted(), 1)) throw new ServiceException("正式结算单不存在");
|
||||
return entity;
|
||||
}
|
||||
|
||||
private FormalSettlement editable(Long id) {
|
||||
FormalSettlement entity = existing(id);
|
||||
if (!TransportBusiConstant.DRAFT.equals(entity.getApprovalStatus()) && !TransportBusiConstant.RETURNED.equals(entity.getApprovalStatus())) throw new ServiceException("仅草稿或已驳回的正式结算单允许编辑");
|
||||
|
||||
+9
-1
@@ -701,7 +701,7 @@ public class InvoiceApplicationServiceImpl extends BaseServiceImpl<InvoiceApplic
|
||||
@Override
|
||||
@Transactional(rollbackFor = Exception.class)
|
||||
public String doSyncKingdee(Long id) {
|
||||
InvoiceApplication entity = existing(id);
|
||||
InvoiceApplication entity = lockedExisting(id);
|
||||
if (!TransportBusiConstant.APPROVED.equals(entity.getApprovalStatus())) throw new ServiceException("仅审批通过的开票申请允许同步金蝶");
|
||||
// 已同步/已开票幂等返回(开票完成为终态);星瀚内码由附件补传分支经 A303-4 反查回填
|
||||
if (KingdeeBfiConstant.KINGDEE_STATUS_SYNCED.equals(entity.getKingdeeStatus())
|
||||
@@ -1669,6 +1669,14 @@ public class InvoiceApplicationServiceImpl extends BaseServiceImpl<InvoiceApplic
|
||||
return entity;
|
||||
}
|
||||
|
||||
/** 行锁读:同一单据并发推送串行化(锁随 doSyncKingdee 事务提交释放,后者读到已同步状态幂等返回) */
|
||||
private InvoiceApplication lockedExisting(Long id) {
|
||||
InvoiceApplication entity = baseMapper.selectOne(Wrappers.<InvoiceApplication>lambdaQuery()
|
||||
.eq(InvoiceApplication::getId, id).last("FOR UPDATE"));
|
||||
if (entity == null || Objects.equals(entity.getIsDeleted(), 1)) throw new ServiceException("开票申请不存在");
|
||||
return entity;
|
||||
}
|
||||
|
||||
private InvoiceApplication editable(Long id) {
|
||||
InvoiceApplication entity = existing(id);
|
||||
if (!List.of(TransportBusiConstant.DRAFT, TransportBusiConstant.RETURNED).contains(entity.getApprovalStatus())) throw new ServiceException("当前状态不可编辑");
|
||||
|
||||
Reference in New Issue
Block a user