diff --git a/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/InvoiceApplicationServiceImpl.java b/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/InvoiceApplicationServiceImpl.java index 46af949b..4865f443 100644 --- a/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/InvoiceApplicationServiceImpl.java +++ b/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/InvoiceApplicationServiceImpl.java @@ -1158,7 +1158,8 @@ public class InvoiceApplicationServiceImpl extends BaseServiceImpl applicationBySerialNo = new LinkedHashMap<>(); + Map> serialNosByApplicationId = new LinkedHashMap<>(); applications.forEach(application -> { if (Func.isNotBlank(application.getKingdeeBillNo())) { // 多张发票时申请单金蝶单号逗号拼接存储,拆分为逐张单号分别归集回写 for (String serialNo : application.getKingdeeBillNo().split(",")) { if (Func.isNotBlank(serialNo)) { applicationBySerialNo.putIfAbsent(serialNo.trim(), application); + serialNosByApplicationId.computeIfAbsent(application.getId(), key -> new ArrayList<>()).add(serialNo.trim()); } } } }); + // 已有开票结果的单号归集(含历史已落库),全部张次齐备才推进开票完成 + Set serialNosWithResult = new LinkedHashSet<>(); Map sellerCache = new LinkedHashMap<>(); Map> serialNosBySellerTaxNo = new LinkedHashMap<>(); int unresolved = 0; @@ -1211,7 +1216,6 @@ public class InvoiceApplicationServiceImpl extends BaseServiceImpl> group : serialNosBySellerTaxNo.entrySet()) { List groupSerialNos = group.getValue(); for (int from = 0; from < groupSerialNos.size(); from += INVOICE_RESULT_QUERY_BATCH) { @@ -1232,10 +1236,11 @@ public class InvoiceApplicationServiceImpl extends BaseServiceImpl existingInvoiceMap = batchQueryExistingInvoices(batch); log.debug("金蝶开票结果回写:批次已存在发票记录数={}", existingInvoiceMap.size()); - // 收集待插入的发票记录、待补文件地址的已有发票记录和待更新的开票申请 + // 已落库记录对应的单号视为已有开票结果(跨批次幂等归集) + existingInvoiceMap.values().forEach(record -> serialNosWithResult.add(Func.toStr(record.getSerialNo()).trim())); + // 收集待插入的发票记录和待补文件地址的已有发票记录 List toInsertInvoices = new ArrayList<>(); List toPatchInvoices = new ArrayList<>(); - List toUpdateApplications = new ArrayList<>(); for (BfiInvoiceApplyOpenApiBillVO bill : result.getData()) { String billNo = bill.getBillNo(); InvoiceApplication application = applicationBySerialNo.get(billNo); @@ -1277,13 +1282,8 @@ public class InvoiceApplicationServiceImpl extends BaseServiceImpl 0) { invoiceWritten += inserted; - // 查到发票:开票申请单推进开票完成(终态) - application.setKingdeeStatus(KingdeeBfiConstant.KINGDEE_STATUS_INVOICED); - // HCS 开票登记待更新:扫描任务凭 hcs_fd_id 走 C111-3 回填票据日期(D12) - application.setHcsSyncStatus(HcsSyncConstant.HCS_STATUS_UNSYNCED); - toUpdateApplications.add(application); - invoicedCount++; - log.info("金蝶开票结果回写:开票申请[{}]状态推进为invoiced,本次写入发票{}张", application.getApplicationNo(), inserted); + serialNosWithResult.add(billNo); + log.info("金蝶开票结果回写:单据编号[{}]写入发票{}张", billNo, inserted); } } // 批量插入发票记录 @@ -1296,17 +1296,29 @@ public class InvoiceApplicationServiceImpl extends BaseServiceImpl toCompleteApplications = new ArrayList<>(); + for (InvoiceApplication application : applications) { + List applicationSerialNos = serialNosByApplicationId.get(application.getId()); + if (Func.isEmpty(applicationSerialNos) || !serialNosWithResult.containsAll(applicationSerialNos)) { + continue; + } + application.setKingdeeStatus(KingdeeBfiConstant.KINGDEE_STATUS_INVOICED); + // HCS 开票登记待更新:扫描任务凭 hcs_fd_id 走 C111-3 回填票据日期(D12) + application.setHcsSyncStatus(HcsSyncConstant.HCS_STATUS_UNSYNCED); + toCompleteApplications.add(application); + } + int invoicedCount = toCompleteApplications.size(); + if (!toCompleteApplications.isEmpty()) { + updateBatchById(toCompleteApplications); + log.info("金蝶开票结果回写:批量推进开票完成{}笔", invoicedCount); + } log.info("金蝶开票结果回写完成:待查开票申请{}笔(销方税号无法解析跳过{}笔),回写发票{}张(开票完成{}笔,失败批次{}个)", applications.size(), unresolved, invoiceWritten, invoicedCount, failed); return "金蝶开票结果回写完成:待查开票申请" + applications.size() + "笔(销方税号无法解析跳过" + unresolved