diff --git a/blade-common/src/main/java/org/springblade/common/excel/ImportFailureExcelUtil.java b/blade-common/src/main/java/org/springblade/common/excel/ImportFailureExcelUtil.java index 061b301..70d7183 100644 --- a/blade-common/src/main/java/org/springblade/common/excel/ImportFailureExcelUtil.java +++ b/blade-common/src/main/java/org/springblade/common/excel/ImportFailureExcelUtil.java @@ -128,12 +128,20 @@ public class ImportFailureExcelUtil { } private static List excelFields(Class excelClass) { - return Arrays.stream(excelClass.getDeclaredFields()) - .filter(field -> field.getAnnotation(ExcelProperty.class) != null) - .filter(field -> field.getAnnotation(ExcelIgnore.class) == null) - .filter(field -> !Objects.equals(field.getName(), ERROR_MESSAGE_FIELD)) - .filter(field -> !Objects.equals(field.getName(), FAILURE_REASON_FIELD)) - .toList(); + List> classHierarchy = new ArrayList<>(); + for (Class current = excelClass; current != null; current = current.getSuperclass()) { + classHierarchy.add(0, current); + } + List fields = new ArrayList<>(); + for (Class current : classHierarchy) { + Arrays.stream(current.getDeclaredFields()) + .filter(field -> field.getAnnotation(ExcelProperty.class) != null) + .filter(field -> field.getAnnotation(ExcelIgnore.class) == null) + .filter(field -> !Objects.equals(field.getName(), ERROR_MESSAGE_FIELD)) + .filter(field -> !Objects.equals(field.getName(), FAILURE_REASON_FIELD)) + .forEach(fields::add); + } + return fields; } private static List> buildHead(List excelFields) { diff --git a/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/FormalSettlementVO.java b/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/FormalSettlementVO.java index 8d636c5..1e50737 100644 --- a/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/FormalSettlementVO.java +++ b/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/FormalSettlementVO.java @@ -36,6 +36,7 @@ public class FormalSettlementVO extends FormalSettlement { @TableField(exist = false) @DateTimeFormat(pattern = "yyyy-MM-dd") private LocalDate createStartDate; @TableField(exist = false) @DateTimeFormat(pattern = "yyyy-MM-dd") private LocalDate createEndDate; @TableField(exist = false) private String createUserName; + @TableField(exist = false) private String ids; @TableField(exist = false) private String approvalStatusName; @TableField(exist = false) private String settlementTypeName; @TableField(exist = false) private String preSettlementNos; diff --git a/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/PreSettlementVO.java b/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/PreSettlementVO.java index 51a4ccd..f4573a6 100644 --- a/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/PreSettlementVO.java +++ b/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/PreSettlementVO.java @@ -69,6 +69,9 @@ public class PreSettlementVO extends PreSettlement { @Schema(description = "创建人姓名") private String createUserName; + @TableField(exist = false) + private String ids; + @TableField(exist = false) @Schema(description = "更新人姓名") private String updateUserName; diff --git a/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/TransportReconciliationVO.java b/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/TransportReconciliationVO.java index 5b7ebda..d498905 100644 --- a/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/TransportReconciliationVO.java +++ b/blade-service-api/blade-transport-api/src/main/java/org/springblade/transport/pojo/vo/TransportReconciliationVO.java @@ -18,6 +18,7 @@ import java.util.List; public class TransportReconciliationVO extends TransportReconciliation { @Serial private static final long serialVersionUID = 1L; @TableField(exist = false) private String createUserName; + @TableField(exist = false) private String ids; @TableField(exist = false) private String updateUserName; @TableField(exist = false) private String reconciliationModeName; @TableField(exist = false) private String reconciliationStatusName; diff --git a/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/FormalSettlementController.java b/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/FormalSettlementController.java index 758fcb5..49535ce 100644 --- a/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/FormalSettlementController.java +++ b/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/FormalSettlementController.java @@ -10,14 +10,18 @@ package org.springblade.transport.controller; import com.baomidou.mybatisplus.core.metadata.IPage; import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport; +import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import io.swagger.v3.oas.annotations.Operation; import io.swagger.v3.oas.annotations.tags.Tag; +import jakarta.servlet.http.HttpServletResponse; import lombok.AllArgsConstructor; import org.springblade.core.boot.ctrl.BladeController; +import org.springblade.core.excel.util.ExcelUtil; import org.springblade.core.mp.support.Condition; import org.springblade.core.mp.support.Query; import org.springblade.core.secure.annotation.PreAuth; import org.springblade.core.tool.api.R; +import org.springblade.core.tool.utils.DateUtil; import org.springblade.transport.pojo.dto.FormalSettlementSaveRequest; import org.springblade.transport.pojo.dto.FormalSettlementPaymentRequest; import org.springblade.transport.pojo.dto.FormalSettlementBatchPaymentRequest; @@ -26,6 +30,7 @@ import org.springblade.transport.pojo.dto.FormalSettlementInvoiceClaimRequest; import org.springblade.transport.pojo.dto.PreSettlementDetailAdjustRequest; import org.springblade.transport.pojo.entity.FormalSettlementDetailFee; import org.springblade.transport.pojo.vo.FormalSettlementVO; +import org.springblade.transport.excel.FormalSettlementExcel; import org.springblade.transport.pojo.vo.PreSettlementVO; import org.springblade.transport.service.IFormalSettlementService; import org.springblade.transport.service.IPreSettlementService; @@ -39,6 +44,8 @@ import org.springframework.web.bind.annotation.RestController; import java.util.List; import java.util.Map; +import java.math.BigDecimal; +import java.math.RoundingMode; /** * 正式结算单控制器 @@ -62,6 +69,65 @@ public class FormalSettlementController extends BladeController { return R.data(formalSettlementService.selectPage(Condition.getPage(pageQuery), query)); } + @GetMapping("/export") + @ApiOperationSupport(order = 20) + @Operation(summary = "导出正式结算单") + public void export(FormalSettlementVO query, @RequestParam(required = false) String ids, + HttpServletResponse response) { + query.setIds(ids); + IPage page = formalSettlementService.selectPage(new Page<>(1, 100000), query); + List rows = page.getRecords().stream().map(this::toExcel).toList(); + ExcelUtil.export(response, "正式结算单" + DateUtil.time(), "正式结算单", rows, FormalSettlementExcel.class); + } + + private FormalSettlementExcel toExcel(FormalSettlementVO vo) { + FormalSettlementExcel excel = new FormalSettlementExcel(); + excel.setFormalSettlementNo(vo.getFormalSettlementNo()); + excel.setPreSettlementNos(vo.getPreSettlementNos()); + excel.setSourceType(vo.getSourceType()); + excel.setPayerName(vo.getPayerName()); + excel.setPayeeName(vo.getPayeeName()); + excel.setProjectName(vo.getProjectName()); + excel.setDeptName(vo.getDeptName()); + excel.setContractNo(vo.getContractNo()); + excel.setContractName(vo.getContractName()); + excel.setSettlementAmount(formatMoney(vo.getSettlementAmount(), vo.getCurrency())); + excel.setLocalSettlementAmount(formatMoney(vo.getLocalSettlementAmount(), vo.getLocalCurrency())); + excel.setExchangeRate(vo.getExchangeRate() == null ? "" : vo.getExchangeRate().stripTrailingZeros().toPlainString()); + excel.setInvoiceStatusName(invoiceStatusName(vo.getInvoiceStatus(), vo.getSettlementType())); + excel.setPaymentStatusName(paymentStatusName(vo.getPaymentStatus())); + excel.setApprovalStatusName(vo.getApprovalStatusName()); + excel.setKingdeeBillNo(vo.getKingdeeBillNo()); + excel.setCreateUserName(vo.getCreateUserName()); + excel.setCreateTime(vo.getCreateTime()); + return excel; + } + + private String formatMoney(BigDecimal value, String currency) { + if (value == null) return ""; + return value.setScale(2, RoundingMode.HALF_UP).toPlainString() + " " + + (currency == null || currency.isBlank() ? "RMB" : currency); + } + + private String invoiceStatusName(String value, String settlementType) { + boolean payable = "payable".equals(settlementType); + return switch (value == null ? "" : value) { + case "unreceived" -> payable ? "未收票" : "未开票"; + case "partial" -> payable ? "部分收票" : "部分开票"; + case "completed" -> payable ? "已收票" : "已开票"; + default -> value == null || value.isBlank() ? "-" : value; + }; + } + + private String paymentStatusName(String value) { + return switch (value == null ? "" : value) { + case "unpaid" -> "未收/付款"; + case "partial" -> "部分收/付款"; + case "paid" -> "已收/付款"; + default -> value == null || value.isBlank() ? "-" : value; + }; + } + @GetMapping("/detail") @ApiOperationSupport(order = 2) @Operation(summary = "正式结算单详情") diff --git a/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/PreSettlementController.java b/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/PreSettlementController.java index 09ec05a..0892b50 100644 --- a/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/PreSettlementController.java +++ b/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/PreSettlementController.java @@ -224,7 +224,9 @@ public class PreSettlementController extends BladeController { @GetMapping("/export") @ApiOperationSupport(order = 19) @Operation(summary = "导出预结算单") - public void export(PreSettlementVO query, HttpServletResponse response) { + public void export(PreSettlementVO query, @RequestParam(required = false) String ids, + HttpServletResponse response) { + query.setIds(ids); IPage page = preSettlementService.selectPage(new Page<>(1, 100000), query); List rows = page.getRecords().stream().map(this::toExcel).toList(); ExcelUtil.export(response, "预结算单" + DateUtil.time(), "预结算单", rows, PreSettlementExcel.class); diff --git a/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/TransportReconciliationController.java b/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/TransportReconciliationController.java index 7ca7b65..bfdbce7 100644 --- a/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/TransportReconciliationController.java +++ b/blade-service/blade-transport/src/main/java/org/springblade/transport/controller/TransportReconciliationController.java @@ -7,6 +7,7 @@ package org.springblade.transport.controller; import com.baomidou.mybatisplus.core.metadata.IPage; +import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.github.xiaoymin.knife4j.annotations.ApiOperationSupport; import io.swagger.v3.oas.annotations.Operation; import io.swagger.v3.oas.annotations.tags.Tag; @@ -23,6 +24,7 @@ import org.springblade.transport.excel.CargoReconciliationExcel; import org.springblade.transport.excel.CargoReconciliationFailureExcel; import org.springblade.transport.excel.VehicleReconciliationExcel; import org.springblade.transport.excel.VehicleReconciliationFailureExcel; +import org.springblade.transport.excel.TransportReconciliationExportExcel; import org.springblade.transport.pojo.dto.TransportReconciliationManualMatchRequest; import org.springblade.transport.pojo.dto.TransportReconciliationSaveRequest; import org.springblade.transport.pojo.entity.FormalSettlement; @@ -40,6 +42,8 @@ import org.springframework.web.multipart.MultipartFile; import jakarta.servlet.http.HttpServletResponse; import java.util.ArrayList; import java.util.List; +import java.math.BigDecimal; +import java.math.RoundingMode; /** 运输对账单控制器。 @author Chill */ @RestController @@ -57,6 +61,40 @@ public class TransportReconciliationController extends BladeController { return R.data(reconciliationService.selectPage(Condition.getPage(pageQuery), query)); } + @GetMapping("/export") + @ApiOperationSupport(order = 15) + @Operation(summary = "导出运输对账单") + public void export(TransportReconciliationVO query, @RequestParam(required = false) String ids, + HttpServletResponse response) { + query.setIds(ids); + IPage page = reconciliationService.selectPage(new Page<>(1, 100000), query); + List rows = page.getRecords().stream().map(this::toExcel).toList(); + ExcelUtil.export(response, "运输对账" + DateUtil.time(), "运输对账", rows, TransportReconciliationExportExcel.class); + } + + private TransportReconciliationExportExcel toExcel(TransportReconciliationVO vo) { + TransportReconciliationExportExcel excel = new TransportReconciliationExportExcel(); + excel.setReconciliationNo(vo.getReconciliationNo()); + excel.setPayerName(vo.getPayerName()); + excel.setPayeeName(vo.getPayeeName()); + excel.setProjectName(vo.getProjectName()); + excel.setDeptName(vo.getDeptName()); + excel.setContractNo(vo.getContractNo()); + excel.setContractName(vo.getContractName()); + excel.setSettlementAmount(formatMoney(vo.getSettlementAmount())); + excel.setReconciliationModeName(vo.getReconciliationModeName()); + excel.setExternalBillCount(vo.getExternalBillCount()); + excel.setMatchedCount(vo.getMatchedCount()); + excel.setReconciliationStatusName(vo.getReconciliationStatusName()); + excel.setCreateUserName(vo.getCreateUserName()); + excel.setCreateTime(vo.getCreateTime()); + return excel; + } + + private String formatMoney(BigDecimal value) { + return value == null ? "0.00" : value.setScale(2, RoundingMode.HALF_UP).toPlainString(); + } + @GetMapping("/detail") @ApiOperationSupport(order = 2) @Operation(summary = "运输对账详情") diff --git a/blade-service/blade-transport/src/main/java/org/springblade/transport/excel/FormalSettlementExcel.java b/blade-service/blade-transport/src/main/java/org/springblade/transport/excel/FormalSettlementExcel.java new file mode 100644 index 0000000..56ca203 --- /dev/null +++ b/blade-service/blade-transport/src/main/java/org/springblade/transport/excel/FormalSettlementExcel.java @@ -0,0 +1,58 @@ +package org.springblade.transport.excel; + +import cn.idev.excel.annotation.ExcelProperty; +import cn.idev.excel.annotation.write.style.ColumnWidth; +import cn.idev.excel.annotation.write.style.ContentRowHeight; +import cn.idev.excel.annotation.write.style.HeadRowHeight; +import lombok.Data; + +import java.io.Serial; +import java.io.Serializable; +import java.util.Date; + +@Data +@ColumnWidth(22) +@HeadRowHeight(20) +@ContentRowHeight(18) +public class FormalSettlementExcel implements Serializable { + + @Serial + private static final long serialVersionUID = 1L; + + @ExcelProperty("结算单号") + private String formalSettlementNo; + @ExcelProperty("预结算单号") + private String preSettlementNos; + @ExcelProperty("来源") + private String sourceType; + @ExcelProperty("付款方") + private String payerName; + @ExcelProperty("收款方") + private String payeeName; + @ExcelProperty("项目名称") + private String projectName; + @ExcelProperty("所属组织") + private String deptName; + @ExcelProperty("合同编号") + private String contractNo; + @ExcelProperty("合同名称") + private String contractName; + @ExcelProperty("原币结算金额") + private String settlementAmount; + @ExcelProperty("本位币结算金额") + private String localSettlementAmount; + @ExcelProperty("结算汇率") + private String exchangeRate; + @ExcelProperty("发票状态") + private String invoiceStatusName; + @ExcelProperty("收付款状态") + private String paymentStatusName; + @ExcelProperty("审核状态") + private String approvalStatusName; + @ExcelProperty("金蝶单据号") + private String kingdeeBillNo; + @ExcelProperty("创建人") + private String createUserName; + @ExcelProperty("创建时间") + private Date createTime; +} diff --git a/blade-service/blade-transport/src/main/java/org/springblade/transport/excel/TransportReconciliationExportExcel.java b/blade-service/blade-transport/src/main/java/org/springblade/transport/excel/TransportReconciliationExportExcel.java new file mode 100644 index 0000000..3946455 --- /dev/null +++ b/blade-service/blade-transport/src/main/java/org/springblade/transport/excel/TransportReconciliationExportExcel.java @@ -0,0 +1,50 @@ +package org.springblade.transport.excel; + +import cn.idev.excel.annotation.ExcelProperty; +import cn.idev.excel.annotation.write.style.ColumnWidth; +import cn.idev.excel.annotation.write.style.ContentRowHeight; +import cn.idev.excel.annotation.write.style.HeadRowHeight; +import lombok.Data; + +import java.io.Serial; +import java.io.Serializable; +import java.util.Date; + +@Data +@ColumnWidth(22) +@HeadRowHeight(20) +@ContentRowHeight(18) +public class TransportReconciliationExportExcel implements Serializable { + + @Serial + private static final long serialVersionUID = 1L; + + @ExcelProperty("对账单号") + private String reconciliationNo; + @ExcelProperty("付款方") + private String payerName; + @ExcelProperty("收款方") + private String payeeName; + @ExcelProperty("项目名称") + private String projectName; + @ExcelProperty("所属组织") + private String deptName; + @ExcelProperty("合同编号") + private String contractNo; + @ExcelProperty("合同名称") + private String contractName; + @ExcelProperty("结算金额") + private String settlementAmount; + @ExcelProperty("对账模式") + private String reconciliationModeName; + @ExcelProperty("账单总数") + private Integer externalBillCount; + @ExcelProperty("匹配数") + private Integer matchedCount; + @ExcelProperty("对账状态") + private String reconciliationStatusName; + @ExcelProperty("创建人") + private String createUserName; + @ExcelProperty("创建时间") + private Date createTime; +} diff --git a/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/FormalSettlementServiceImpl.java b/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/FormalSettlementServiceImpl.java index 29cc0a6..5d852e6 100644 --- a/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/FormalSettlementServiceImpl.java +++ b/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/FormalSettlementServiceImpl.java @@ -153,6 +153,9 @@ public class FormalSettlementServiceImpl extends BaseServiceImpl ids = sourceMapper.selectList(Wrappers.lambdaQuery() .like(FormalSettlementSource::getPreSettlementNo, query.getPreSettlementNo())) diff --git a/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/PreSettlementServiceImpl.java b/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/PreSettlementServiceImpl.java index 0fd3b68..17b80bd 100644 --- a/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/PreSettlementServiceImpl.java +++ b/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/PreSettlementServiceImpl.java @@ -668,7 +668,7 @@ public class PreSettlementServiceImpl extends BaseServiceImpl buildQuery(PreSettlementVO query) { - return Wrappers.lambdaQuery() + LambdaQueryWrapper wrapper = Wrappers.lambdaQuery() .eq(PreSettlement::getIsDeleted, 0) .like(Func.isNotEmpty(query.getPreSettlementNo()), PreSettlement::getPreSettlementNo, query.getPreSettlementNo()) @@ -688,6 +688,10 @@ public class PreSettlementServiceImpl extends BaseServiceImpl candidateMap(ReceivablePayableDetail source) { @@ -725,6 +729,9 @@ public class PreSettlementServiceImpl extends BaseServiceImpllambdaUpdate() .set(ReceivablePayableDetail::getPreSettlementNo, settlement.getPreSettlementNo()) @@ -834,8 +842,9 @@ public class PreSettlementServiceImpl extends BaseServiceImpl sourceFees = sourceFeeMapper.selectList( + Wrappers.lambdaQuery() + .eq(ReceivablePayableCargoFee::getDetailId, source.getId()) + .eq(ReceivablePayableCargoFee::getIsDeleted, 0)); + if (sourceFees.isEmpty() || sourceFees.stream().noneMatch(item -> item.getOriginalAmount() != null)) { + return money(source.getTotalAmount()); + } + return sourceFees.stream().map(ReceivablePayableCargoFee::getOriginalAmount) + .map(this::money).reduce(BigDecimal.ZERO, BigDecimal::add); + } + private void copySourceFees(PreSettlementDetail detail, ReceivablePayableDetail source) { List sourceFees = sourceFeeMapper.selectList( Wrappers.lambdaQuery() @@ -880,7 +901,18 @@ public class PreSettlementServiceImpl extends BaseServiceImpl 1 ? keyParts[1] : ""); - row.setOriginalAmount(money(entry.getValue())); - row.setAdjustAmount(preserveAdjustments && old != null ? money(old.getAdjustAmount()) - : BigDecimal.ZERO.setScale(2)); - row.setSettlementAmount(row.getOriginalAmount().add(row.getAdjustAmount())); + // 原金额是明细首次生成时的快照,多次调整后不得被当前结算金额覆盖。 + // 当前费用聚合值代表调整后的结算金额,差额统一记录为调整金额。 + row.setOriginalAmount(old == null ? money(entry.getValue()) : money(old.getOriginalAmount())); + row.setSettlementAmount(money(entry.getValue())); + row.setAdjustAmount(money(row.getSettlementAmount().subtract(row.getOriginalAmount()))); row.setRemark(old == null ? "" : old.getRemark()); row.setManualFlag(0); summaryFeeMapper.insert(row); @@ -1023,11 +1056,12 @@ public class PreSettlementServiceImpl extends BaseServiceImpl resolveBillingPlan(List> plans, String planId) { - if ("__matched__".equals(planId)) { - return plans.stream().filter(this::isDefaultPlan).findFirst() - .orElseGet(() -> plans.isEmpty() ? null : plans.get(plans.size() - 1)); - } - if (Func.isEmpty(planId)) { - return plans.stream().filter(this::isDefaultPlan).findFirst() - .orElseGet(() -> plans.isEmpty() ? null : plans.get(plans.size() - 1)); + if ("__matched__".equals(planId) || Func.isEmpty(planId)) { + return resolveDefaultBillingPlan(plans, null); } return plans.stream().filter(plan -> Objects.equals(stringValue(plan, "id"), planId) || Objects.equals(stringValue(plan, "planId"), planId) @@ -1545,20 +1540,24 @@ public class ReceivablePayableDetailServiceImpl return Boolean.TRUE.equals(value) || "true".equalsIgnoreCase(String.valueOf(value)) || "1".equals(String.valueOf(value)); } + /** + * 解析合同生效计费方案。 + * 合同存在勾选默认的计费方案时仅在默认方案内匹配计算,不再回退其他方案; + * 全部方案均未勾选默认时仅使用最新添加的计费方案。 + */ private Map resolveDefaultBillingPlan(List> plans, String transportType) { if (plans.isEmpty()) return null; - if (plans.size() == 1) return plans.get(0); - Optional> matchedDefaultPlan = plans.stream().filter(this::isDefaultPlan) + List> defaultPlans = plans.stream().filter(this::isDefaultPlan).toList(); + if (defaultPlans.isEmpty()) return plans.get(plans.size() - 1); + Optional> matchedDefaultPlan = defaultPlans.stream() .filter(plan -> !isBlank(plan.get("transportMode"))) .filter(plan -> matchesCondition(plan.get("transportMode"), transportType)) .findFirst(); if (matchedDefaultPlan.isPresent()) return matchedDefaultPlan.get(); - Optional> defaultPlanWithoutTransportMode = plans.stream() - .filter(this::isDefaultPlan) + return defaultPlans.stream() .filter(plan -> isBlank(plan.get("transportMode"))) - .findFirst(); - if (defaultPlanWithoutTransportMode.isPresent()) return defaultPlanWithoutTransportMode.get(); - return plans.stream().noneMatch(this::isDefaultPlan) ? plans.get(plans.size() - 1) : null; + .findFirst() + .orElseGet(() -> defaultPlans.get(defaultPlans.size() - 1)); } private BigDecimal calculateRule(Map rule, Waybill waybill) { @@ -1937,42 +1936,28 @@ public class ReceivablePayableDetailServiceImpl return waybill; } + /** + * 匹配费用调整试算使用的合同计费规则,仅在合同生效计费方案内查找。 + */ private List> matchingAdjustedRules(ContractManage contract, ReceivablePayableCargoFee fee, Waybill waybill) { + Map plan = resolveDefaultBillingPlan(parseList(contract.getBillingPlanJson()), + waybill.getTransportType()); + if (plan == null || !(plan.get("rules") instanceof List rules)) return List.of(); Set feeItemNames = parseMap(fee.getFeeItemsJson()).keySet(); - List> firstCandidates = List.of(); - List> defaultCandidates = List.of(); - List> billingMatchedCandidates = List.of(); - List> billingFieldCandidates = List.of(); - for (Map plan : parseList(contract.getBillingPlanJson())) { - if (!(plan.get("rules") instanceof List rules)) continue; - List> candidates = new ArrayList<>(); - List> feeItemCandidates = new ArrayList<>(); - for (Object value : rules) { - if (!(value instanceof Map raw)) continue; - Map rule = new LinkedHashMap<>(); - raw.forEach((key, item) -> rule.put(String.valueOf(key), item)); - if (!feeItemNames.contains(stringValue(rule, "feeItem"))) continue; - feeItemCandidates.add(rule); - if (matchesRule(rule, waybill)) candidates.add(rule); - } - if (feeItemCandidates.stream().anyMatch(rule -> matchesBillingFields(rule, fee))) { - if (billingFieldCandidates.isEmpty() || isDefaultPlan(plan)) { - billingFieldCandidates = feeItemCandidates; - } - } - if (candidates.isEmpty()) continue; - if (firstCandidates.isEmpty()) firstCandidates = candidates; - if (isDefaultPlan(plan)) defaultCandidates = candidates; - if (candidates.stream().anyMatch(rule -> matchesBillingFields(rule, fee))) { - if (billingMatchedCandidates.isEmpty() || isDefaultPlan(plan)) { - billingMatchedCandidates = candidates; - } - } + List> feeItemCandidates = new ArrayList<>(); + List> candidates = new ArrayList<>(); + for (Object value : rules) { + if (!(value instanceof Map raw)) continue; + Map rule = new LinkedHashMap<>(); + raw.forEach((key, item) -> rule.put(String.valueOf(key), item)); + if (!feeItemNames.contains(stringValue(rule, "feeItem"))) continue; + feeItemCandidates.add(rule); + if (matchesRule(rule, waybill)) candidates.add(rule); } - if (!billingMatchedCandidates.isEmpty()) return billingMatchedCandidates; - if (!billingFieldCandidates.isEmpty()) return billingFieldCandidates; - return defaultCandidates.isEmpty() ? firstCandidates : defaultCandidates; + if (candidates.stream().anyMatch(rule -> matchesBillingFields(rule, fee))) return candidates; + if (feeItemCandidates.stream().anyMatch(rule -> matchesBillingFields(rule, fee))) return feeItemCandidates; + return candidates; } private boolean matchesBillingFields(Map rule, ReceivablePayableCargoFee fee) { diff --git a/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/TransportReconciliationServiceImpl.java b/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/TransportReconciliationServiceImpl.java index 121ca59..410e974 100644 --- a/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/TransportReconciliationServiceImpl.java +++ b/blade-service/blade-transport/src/main/java/org/springblade/transport/service/impl/TransportReconciliationServiceImpl.java @@ -116,6 +116,9 @@ public class TransportReconciliationServiceImpl .eq(Func.isNotEmpty(query.getMatchStatus()), TransportReconciliation::getMatchStatus, query.getMatchStatus()) .eq(Func.isNotEmpty(query.getReconciliationStatus()), TransportReconciliation::getReconciliationStatus, query.getReconciliationStatus()) .orderByDesc(TransportReconciliation::getCreateTime); + if (Func.isNotEmpty(query.getIds())) { + wrapper.in(TransportReconciliation::getId, Func.toLongList(query.getIds())); + } return page(page, wrapper).convert(item -> TransportReconciliationWrapper.build().entityVO(item)); } diff --git a/doc/sql/transport/blade_tms_business.sql b/doc/sql/transport/blade_tms_business.sql index 5739a02..16d2341 100644 --- a/doc/sql/transport/blade_tms_business.sql +++ b/doc/sql/transport/blade_tms_business.sql @@ -417,6 +417,7 @@ INSERT IGNORE INTO `blade_menu` (`id`, `parent_id`, `code`, `name`, `alias`, `pa (2090000000000000612, 2090000000000000600, 'waybill_manage_template', '下载模板', 'waybill_manage_template', '', '', 12, 2, 0, 1, NULL, '', 0), (2090000000000000613, 2090000000000000600, 'waybill_manage_road_loading', '公路配载', 'waybill_manage_road_loading', '', '', 13, 2, 0, 1, NULL, '', 0), (2090000000000000614, 2090000000000000600, 'waybill_manage_mileage', '维护里程', 'waybill_manage_mileage', '', '', 14, 2, 0, 1, NULL, '', 0), +(2090000000000000615, 2090000000000000000, 'waybill_import', '导入运单', 'waybill_import', '/business/waybill-import', 'iconfont icon-daoru', 65, 1, 0, 1, NULL, '', 0), (2090000000000000700, 2090000000000000000, 'loading_manage', '配载管理', 'loading_manage', '/business/loading-manage', 'iconfont icon-caidanguanli', 70, 1, 0, 1, NULL, '', 0), (2090000000000000701, 2090000000000000700, 'loading_manage_view', '查看', 'loading_manage_view', '', '', 1, 2, 0, 1, NULL, '', 0), (2090000000000000702, 2090000000000000700, 'loading_manage_add', '新增', 'loading_manage_add', '', '', 2, 2, 0, 1, NULL, '', 0),