src/main/java/com/ruoyi/purchase/service/impl/PurchaseLedgerServiceImpl.java
@@ -17,13 +17,11 @@
import com.ruoyi.basic.mapper.ProductMapper;
import com.ruoyi.basic.mapper.ProductModelMapper;
import com.ruoyi.basic.mapper.SupplierManageMapper;
import com.ruoyi.basic.pojo.Customer;
import com.ruoyi.basic.pojo.Product;
import com.ruoyi.basic.pojo.ProductModel;
import com.ruoyi.basic.pojo.SupplierManage;
import com.ruoyi.common.enums.FileNameType;
import com.ruoyi.common.exception.base.BaseException;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.common.utils.poi.ExcelUtil;
@@ -50,18 +48,19 @@
import com.ruoyi.sales.pojo.InvoiceRegistrationProduct;
import com.ruoyi.sales.pojo.SalesLedger;
import com.ruoyi.sales.pojo.SalesLedgerProduct;
import lombok.RequiredArgsConstructor;
import com.ruoyi.sales.service.impl.CommonFileServiceImpl;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.io.FilenameUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.MultipartFile;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.nio.file.Files;
@@ -83,51 +82,71 @@
 * @date 2025-05-09
 */
@Service
@RequiredArgsConstructor
@Slf4j
public class PurchaseLedgerServiceImpl extends ServiceImpl<PurchaseLedgerMapper, PurchaseLedger> implements IPurchaseLedgerService {
    private final AccountExpenseService accountExpenseService;
    private final PurchaseLedgerMapper purchaseLedgerMapper;
    @Autowired
    private  AccountExpenseService accountExpenseService;
    @Autowired
    private  PurchaseLedgerMapper purchaseLedgerMapper;
    private final SalesLedgerMapper salesLedgerMapper;
    private final SalesLedgerProductMapper salesLedgerProductMapper;
    @Autowired
    private  SalesLedgerMapper salesLedgerMapper;
    @Autowired
    private  SalesLedgerProductMapper salesLedgerProductMapper;
    private final SysUserMapper userMapper;
    @Autowired
    private  SysUserMapper userMapper;
    private final TempFileMapper tempFileMapper;
    @Autowired
    private  TempFileMapper tempFileMapper;
    private final CommonFileMapper commonFileMapper;
    @Autowired
    private  CommonFileMapper commonFileMapper;
    private final SupplierManageMapper supplierManageMapper;
    @Autowired
    private  SupplierManageMapper supplierManageMapper;
    private final ProductMapper productMapper;
    @Autowired
    private  ProductMapper productMapper;
    private final ProductModelMapper productModelMapper;
    @Autowired
    private  ProductModelMapper productModelMapper;
    private final SysUserMapper sysUserMapper;
    @Autowired
    private  SysUserMapper sysUserMapper;
    private final TicketRegistrationMapper ticketRegistrationMapper;
    @Autowired
    private  TicketRegistrationMapper ticketRegistrationMapper;
    private final ProductRecordMapper productRecordMapper;
    @Autowired
    private  ProductRecordMapper productRecordMapper;
    private final PaymentRegistrationMapper paymentRegistrationMapper;
    private final InvoiceRegistrationProductMapper invoiceRegistrationProductMapper;
    private final StringRedisTemplate redisTemplate;
    private final QualityInspectMapper qualityInspectMapper;
    private final QualityTestStandardBindingMapper qualityTestStandardBindingMapper;
    private final QualityTestStandardParamMapper qualityTestStandardParamMapper;
    private final QualityTestStandardMapper qualityTestStandardMapper;
    private final QualityInspectParamMapper qualityInspectParamMapper;
    private final ApproveProcessServiceImpl approveProcessService;
    private final ProcurementRecordMapper procurementRecordStorageMapper;
    private final PurchaseLedgerTemplateMapper purchaseLedgerTemplateMapper;
    private final SalesLedgerProductTemplateMapper salesLedgerProductTemplateMapper;
    @Autowired
    private  PaymentRegistrationMapper paymentRegistrationMapper;
    @Autowired
    private  InvoiceRegistrationProductMapper invoiceRegistrationProductMapper;
    @Autowired
    private  StringRedisTemplate redisTemplate;
    @Autowired
    private  QualityInspectMapper qualityInspectMapper;
    @Autowired
    private  CommonFileServiceImpl commonFileService;
    @Autowired
    private  QualityTestStandardBindingMapper qualityTestStandardBindingMapper;
    @Autowired
    private  QualityTestStandardParamMapper qualityTestStandardParamMapper;
    @Autowired
    private  QualityTestStandardMapper qualityTestStandardMapper;
    @Autowired
    private  QualityInspectParamMapper qualityInspectParamMapper;
    @Autowired
    private  ApproveProcessServiceImpl approveProcessService;
    @Autowired
    private  ProcurementRecordMapper procurementRecordStorageMapper;
    @Autowired
    private  PurchaseLedgerTemplateMapper purchaseLedgerTemplateMapper;
    @Autowired
    private  SalesLedgerProductTemplateMapper salesLedgerProductTemplateMapper;
    @Value("${file.upload-dir}")
    private String uploadDir;
@@ -137,7 +156,43 @@
        if (StringUtils.isNotBlank(purchaseLedger.getPurchaseContractNumber())) {
            queryWrapper.like(PurchaseLedger::getPurchaseContractNumber, purchaseLedger.getPurchaseContractNumber());
        }
        return purchaseLedgerMapper.selectList(queryWrapper);
        if (purchaseLedger.getSupplierId() != null) {
            queryWrapper.eq(PurchaseLedger::getSupplierId, purchaseLedger.getSupplierId());
        }
        if (purchaseLedger.getApprovalStatus() != null) {
            queryWrapper.eq(PurchaseLedger::getApprovalStatus, purchaseLedger.getApprovalStatus());
        }
        if (StringUtils.isNotBlank(purchaseLedger.getSupplierName())) {
            queryWrapper.like(PurchaseLedger::getSupplierName, purchaseLedger.getSupplierName());
        }
        if (StringUtils.isNotBlank(purchaseLedger.getSalesContractNo())) {
            queryWrapper.like(PurchaseLedger::getSalesContractNo, purchaseLedger.getSalesContractNo());
        }
        if (StringUtils.isNotBlank(purchaseLedger.getProjectName())) {
            queryWrapper.like(PurchaseLedger::getProjectName, purchaseLedger.getProjectName());
        }
        queryWrapper.orderByDesc(PurchaseLedger::getEntryDate);
        List<PurchaseLedger> list = purchaseLedgerMapper.selectList(queryWrapper);
        if (CollectionUtils.isNotEmpty(list)) {
            Set<Long> supplierIds = list.stream()
                    .map(PurchaseLedger::getSupplierId)
                    .filter(Objects::nonNull)
                    .collect(Collectors.toSet());
            if (!supplierIds.isEmpty()) {
                List<SupplierManage> suppliers = supplierManageMapper.selectBatchIds(supplierIds);
                Map<Long, Integer> typeMap = suppliers.stream()
                        .collect(Collectors.toMap(SupplierManage::getId, SupplierManage::getSupplierType, (k1, k2) -> k1));
                list.forEach(item -> {
                    if (item.getSupplierId() != null) {
                        item.setPurchaseType(typeMap.get(item.getSupplierId()));
                    }
                });
            }
        }
        return list;
    }
    @Override
@@ -148,7 +203,10 @@
        //录入人
        SysUser sysUser = userMapper.selectUserById(purchaseLedgerDto.getRecorderId());
        SupplierManage supplierManage = supplierManageMapper.selectById(purchaseLedgerDto.getSupplierId());
        SupplierManage supplierManage = null;
        if (purchaseLedgerDto.getSupplierId() != null) {
            supplierManage = supplierManageMapper.selectById(purchaseLedgerDto.getSupplierId());
        }
        // DTO转Entity
        PurchaseLedger purchaseLedger = new PurchaseLedger();
@@ -159,10 +217,11 @@
        }
        purchaseLedger.setSalesContractNo(ObjectUtils.isNotEmpty(salesLedger) ? salesLedger.getSalesContractNo() : "");
        purchaseLedger.setSalesLedgerId(ObjectUtils.isNotEmpty(salesLedger) ? salesLedger.getId() : -1);
        purchaseLedger.setSupplierName(supplierManage.getSupplierName());
        purchaseLedger.setSupplierName(supplierManage != null ? supplierManage.getSupplierName() : purchaseLedgerDto.getSupplierName());
        purchaseLedger.setRecorderId(purchaseLedgerDto.getRecorderId());
        purchaseLedger.setRecorderName(sysUser.getNickName());
        purchaseLedger.setPhoneNumber(sysUser.getPhonenumber());
        purchaseLedger.setApprovalStatus(1);
        // 3. 新增或更新主表
        if (purchaseLedger.getId() == null) {
            purchaseLedgerMapper.insert(purchaseLedger);
@@ -186,15 +245,15 @@
        if (productList != null && !productList.isEmpty()) {
            handleSalesLedgerProducts(purchaseLedger.getId(), productList, purchaseLedgerDto.getType());
        }
        //新增原材料检验
        if (productList != null) {
            for (SalesLedgerProduct saleProduct : productList) {
                //是否推送质检,如果true就添加
                if (saleProduct.getIsChecked()) {
                    addQualityInspect(purchaseLedger, saleProduct);
                }
            }
        }
        //新增原材料检验  审批之后才生成检验
//        if (productList != null) {
//            for (SalesLedgerProduct saleProduct : productList) {
//                //是否推送质检,如果true就添加
//                if (saleProduct.getIsChecked()) {
//                    addQualityInspect(purchaseLedger, saleProduct);
//                }
//            }
//        }
        // 5. 迁移临时文件到正式目录
        if (purchaseLedgerDto.getTempFileIds() != null && !purchaseLedgerDto.getTempFileIds().isEmpty()) {
            migrateTempFilesToFormal(purchaseLedger.getId(), purchaseLedgerDto.getTempFileIds());
@@ -202,7 +261,8 @@
        return 1;
    }
    private void addQualityInspect(PurchaseLedger purchaseLedger, SalesLedgerProduct saleProduct) {
    public void addQualityInspect(PurchaseLedger purchaseLedger, SalesLedgerProduct saleProduct) {
        QualityInspect qualityInspect = new QualityInspect();
        qualityInspect.setInspectType(0);
        qualityInspect.setSupplier(purchaseLedger.getSupplierName());
@@ -298,22 +358,29 @@
                LocalDateTime localDateTime = entryDate.toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime();
                salesLedgerProduct.setRegisterDate(localDateTime);
                salesLedgerProduct.setFutureTickets(salesLedgerProduct.getQuantity());
                salesLedgerProduct.setFutureTicketsAmount(salesLedgerProduct.getTaxInclusiveTotalPrice());
                salesLedgerProduct.setPendingTicketsTotal(salesLedgerProduct.getTaxInclusiveTotalPrice());
                if (Integer.valueOf(2).equals(purchaseLedger.getPurchaseType())) {
                    salesLedgerProduct.setFutureTicketsAmount(salesLedgerProduct.getTotalPrice() != null ? salesLedgerProduct.getTotalPrice() : BigDecimal.ZERO);
                    salesLedgerProduct.setPendingTicketsTotal(salesLedgerProduct.getTotalPrice() != null ? salesLedgerProduct.getTotalPrice() : BigDecimal.ZERO);
                } else {
                    salesLedgerProduct.setFutureTicketsAmount(salesLedgerProduct.getTaxInclusiveTotalPrice());
                    salesLedgerProduct.setPendingTicketsTotal(salesLedgerProduct.getTaxInclusiveTotalPrice());
                }
                salesLedgerProductMapper.insert(salesLedgerProduct);
            }
        }
        // 计算总含税金额
        BigDecimal totalTaxInclusiveAmount = products.stream()
                .map(SalesLedgerProduct::getTaxInclusiveTotalPrice)
        // 计算总金额
        BigDecimal totalAmount = products.stream()
                .map(p -> Integer.valueOf(2).equals(purchaseLedger.getPurchaseType()) ?
                        (p.getTotalPrice() != null ? p.getTotalPrice() : BigDecimal.ZERO) :
                        (p.getTaxInclusiveTotalPrice() != null ? p.getTaxInclusiveTotalPrice() : BigDecimal.ZERO))
                .filter(Objects::nonNull)
                .reduce(BigDecimal.ZERO, BigDecimal::add);
        // 更新主表的总金额字段
        if (salesLedgerId != null) {
            // 直接更新指定ID的记录的contractAmount字段为totalTaxInclusiveAmount
            purchaseLedgerMapper.updateContractAmountById(salesLedgerId, totalTaxInclusiveAmount);
            // 直接更新指定ID的记录的contractAmount字段为totalAmount
            purchaseLedgerMapper.updateContractAmountById(salesLedgerId, totalAmount);
        }
    }
@@ -397,6 +464,12 @@
        if (ids == null || ids.length == 0) {
           throw new BaseException("请选中至少一条数据");
        }
        for (Long id : ids) {
            PurchaseLedger purchaseLedger = purchaseLedgerMapper.selectById(id);
            if (purchaseLedger.getApprovalStatus().equals(3)) {
                throw new BaseException(purchaseLedger.getPurchaseContractNumber()+"已经审批通过,不允许删除");
            }
        }
        // 批量删除关联的采购入库记录
        LambdaQueryWrapper<SalesLedgerProduct> salesLedgerProductQueryWrapper = new LambdaQueryWrapper<>();
        salesLedgerProductQueryWrapper.in(SalesLedgerProduct::getSalesLedgerId, ids)
@@ -430,6 +503,7 @@
        //批量删除检验标准
        LambdaQueryWrapper<QualityInspect> materialInspectLambdaQueryWrapper = new LambdaQueryWrapper<>();
        materialInspectLambdaQueryWrapper.in(QualityInspect::getPurchaseLedgerId, ids);
        List<QualityInspect> qualityInspects = qualityInspectMapper.selectList(materialInspectLambdaQueryWrapper);
        qualityInspects.stream().forEach(qualityInspect -> {
            if (ObjectUtils.isNotEmpty(qualityInspect.getInspectState())&&qualityInspect.getInspectState().equals(1)) {
@@ -461,6 +535,8 @@
        }
        //批量删除原材料检验数据
        qualityInspectMapper.delete(materialInspectLambdaQueryWrapper);
        //删除附件
        commonFileService.deleteByBusinessIds(Arrays.asList(ids), 2);
        // 批量删除采购台账
        return purchaseLedgerMapper.deleteBatchIds(Arrays.asList(ids));
    }
@@ -621,14 +697,14 @@
    public AjaxResult importData(MultipartFile file) {
        LoginUser loginUser = SecurityUtils.getLoginUser();
        try {
            InputStream inputStream = file.getInputStream();
            byte[] fileBytes = file.getBytes();
            ExcelUtil<PurchaseLedgerImportDto> salesLedgerImportDtoExcelUtil = new ExcelUtil<>(PurchaseLedgerImportDto.class);
            Map<String, List<PurchaseLedgerImportDto>> stringListMap = salesLedgerImportDtoExcelUtil.importExcelMultiSheet(Arrays.asList("采购台账数据", "采购产品数据"), inputStream, 0);
            if (CollectionUtils.isEmpty(stringListMap)) return AjaxResult.error("采购表格为空!");
            // 业务层合并
            List<PurchaseLedgerImportDto> salesLedgerImportDtoList = stringListMap.get("采购台账数据");
            // 采购台账数据不跳过标题
            List<PurchaseLedgerImportDto> salesLedgerImportDtoList = salesLedgerImportDtoExcelUtil.importExcel("采购台账数据", new ByteArrayInputStream(fileBytes), 0);
            // 采购产品数据跳过1行标题
            List<PurchaseLedgerImportDto> salesLedgerProductImportDtoList = salesLedgerImportDtoExcelUtil.importExcel("采购产品数据", new ByteArrayInputStream(fileBytes), 1);
            if (CollectionUtils.isEmpty(salesLedgerImportDtoList)) return AjaxResult.error("采购台账数据为空!");
            List<PurchaseLedgerImportDto> salesLedgerProductImportDtoList = stringListMap.get("采购产品数据");
            if (CollectionUtils.isEmpty(salesLedgerProductImportDtoList)) return AjaxResult.error("采购产品数据为空!");
            // 供应商数据
            List<SupplierManage> customers = supplierManageMapper.selectList(new LambdaQueryWrapper<SupplierManage>().in(SupplierManage::getSupplierName,
@@ -638,14 +714,27 @@
            List<SysUser> sysUsers = sysUserMapper.selectList(new LambdaQueryWrapper<SysUser>().in(SysUser::getNickName,
                    salesLedgerImportDtoList.stream().map(PurchaseLedgerImportDto::getRecorderName).collect(Collectors.toList())));
            for (PurchaseLedgerImportDto salesLedgerImportDto : salesLedgerImportDtoList) {
                PurchaseLedger purchaseLedger = purchaseLedgerMapper.selectOne(new LambdaQueryWrapper<PurchaseLedger>()
                        .eq(PurchaseLedger::getPurchaseContractNumber, salesLedgerImportDto.getPurchaseContractNumber())
                        .last("limit 1"));
                if(purchaseLedger != null){
                    continue;
                }
                PurchaseLedger salesLedger = new PurchaseLedger();
                BeanUtils.copyProperties(salesLedgerImportDto, salesLedger);
                // 通过供应商名称查询ID
                salesLedger.setSupplierId(customers.stream()
                // 查询供应商档案并设置采购类型(对公1/对私2)
                SupplierManage matchedSupplier = customers.stream()
                        .filter(customer -> customer.getSupplierName().equals(salesLedger.getSupplierName()))
                        .findFirst()
                        .map(SupplierManage::getId)
                        .orElse(null));
                        .orElse(null);
                if (matchedSupplier != null) {
                    salesLedger.setSupplierId(matchedSupplier.getId());
                    salesLedger.setPurchaseType(matchedSupplier.getSupplierType());
                } else {
                    salesLedger.setPurchaseType(1); // 默认对公
                }
                Long aLong = sysUsers.stream()
                        .filter(sysUser -> sysUser.getNickName().equals(salesLedger.getRecorderName()))
                        .findFirst()
@@ -654,15 +743,30 @@
                if (aLong == null)
                    throw new RuntimeException("录入人:" + salesLedger.getRecorderName() + ",无对应用户!");
                salesLedger.setRecorderId(aLong);
                // 采购产品数据绑定,通过采购单号获取对应采购产品数据
                // 采购产品数据绑定
                List<PurchaseLedgerProductImportDto> salesLedgerProductImportDtos = salesLedgerProductImportDtoList.stream()
                        .filter(salesLedgerProductImportDto -> salesLedgerProductImportDto.getPurchaseContractNumber().equals(salesLedger.getPurchaseContractNumber()))
                        .collect(Collectors.toList());
                if (CollectionUtils.isEmpty(salesLedgerProductImportDtos))
                    throw new RuntimeException("采购单号:" + salesLedgerImportDto.getPurchaseContractNumber() + ",无对应产品数据!");
                boolean isPrivate = Integer.valueOf(2).equals(salesLedger.getPurchaseType());
                // 统一计算主表合同金额
                salesLedger.setContractAmount(salesLedgerProductImportDtos.stream()
                        .map(PurchaseLedgerProductImportDto::getTaxInclusiveTotalPrice)
                        .reduce(BigDecimal.ZERO,BigDecimal::add));
                        .map(dto -> {
                            if (isPrivate) {
                                if (dto.getTotalPrice() != null) return dto.getTotalPrice();
                                BigDecimal up = dto.getUnitPrice() != null ? dto.getUnitPrice() : BigDecimal.ZERO;
                                BigDecimal qty = dto.getQuantity() != null ? dto.getQuantity() : BigDecimal.ZERO;
                                return up.multiply(qty);
                            } else {
                                return dto.getTaxInclusiveTotalPrice() != null ? dto.getTaxInclusiveTotalPrice() : BigDecimal.ZERO;
                            }
                        })
                        .reduce(BigDecimal.ZERO, BigDecimal::add));
                // 通过销售单号绑定销售
                SalesLedger salesLedger1 = salesLedgerMapper.selectOne(new LambdaQueryWrapper<SalesLedger>()
                        .eq(SalesLedger::getSalesContractNo, salesLedger.getSalesContractNo())
@@ -674,8 +778,8 @@
                // 通过昵称获取用户ID
                String[] split = salesLedger.getApproveUserIds().split(",");
                List<Long> ids = new ArrayList<>();
                for (int i = 0; i < split.length; i++) {
                    SysUser sysUser = sysUserMapper.selectOne(new LambdaQueryWrapper<SysUser>().eq(SysUser::getNickName, split[i])
                for (String s : split) {
                    SysUser sysUser = sysUserMapper.selectOne(new LambdaQueryWrapper<SysUser>().eq(SysUser::getNickName, s)
                            .last("LIMIT 1"));
                    if (sysUser != null) {
                        ids.add(sysUser.getUserId());
@@ -691,10 +795,48 @@
                    BeanUtils.copyProperties(salesLedgerProductImportDto, salesLedgerProduct);
                    salesLedgerProduct.setSalesLedgerId(salesLedger.getId());
                    salesLedgerProduct.setType(2);
                    // 计算不含税总价
                    salesLedgerProduct.setTaxExclusiveTotalPrice(salesLedgerProduct.getTaxInclusiveTotalPrice().divide(new BigDecimal(1).add(salesLedgerProduct.getTaxRate().divide(new BigDecimal(100))), 2, RoundingMode.HALF_UP));
                    // 未来票数量
                    salesLedgerProduct.setFutureTickets(salesLedgerProduct.getQuantity());
                    salesLedgerProduct.setFutureTicketsAmount(salesLedgerProduct.getTaxExclusiveTotalPrice());
                    if (isPrivate) {
                        // 对私采购逻辑
                        if (salesLedgerProduct.getTotalPrice() == null && salesLedgerProduct.getUnitPrice() != null && salesLedgerProduct.getQuantity() != null) {
                            salesLedgerProduct.setTotalPrice(salesLedgerProduct.getUnitPrice().multiply(salesLedgerProduct.getQuantity()));
                        }
                        BigDecimal tp = salesLedgerProduct.getTotalPrice() != null ? salesLedgerProduct.getTotalPrice() : BigDecimal.ZERO;
                        salesLedgerProduct.setTaxInclusiveTotalPrice(tp);
                        salesLedgerProduct.setTaxExclusiveTotalPrice(salesLedgerProduct.getUnitPrice() != null ?
                                salesLedgerProduct.getUnitPrice().multiply(salesLedgerProduct.getQuantity()) : tp);
                        //  统一金额
                        salesLedgerProduct.setFutureTicketsAmount(tp);
                        salesLedgerProduct.setPendingTicketsTotal(tp);
                        salesLedgerProduct.setTaxRate(null);
                        salesLedgerProduct.setTaxInclusiveUnitPrice(null);
                        salesLedgerProduct.setInvoiceType(null);
                    } else {
                        // 对公采购逻辑
                        //  补全不含税总价
                        if (salesLedgerProduct.getTaxInclusiveTotalPrice() != null && salesLedgerProduct.getTaxRate() != null) {
                            salesLedgerProduct.setTaxExclusiveTotalPrice(
                                    salesLedgerProduct.getTaxInclusiveTotalPrice()
                                            .divide(new BigDecimal(1).add(salesLedgerProduct.getTaxRate().divide(new BigDecimal(100))), 2, RoundingMode.HALF_UP)
                            );
                        }
                        //  对公统一使用含税总价
                        BigDecimal titp = salesLedgerProduct.getTaxInclusiveTotalPrice() != null ? salesLedgerProduct.getTaxInclusiveTotalPrice() : BigDecimal.ZERO;
                        salesLedgerProduct.setFutureTicketsAmount(titp);
                        salesLedgerProduct.setPendingTicketsTotal(titp);
                        salesLedgerProduct.setUnitPrice(null);
                        salesLedgerProduct.setTotalPrice(null);
                    }
                    // 匹配产品种类和规格型号映射ID
                    list.stream()
                            .filter(map -> map.get("productName").equals(salesLedgerProduct.getProductCategory()) && map.get("model").equals(salesLedgerProduct.getSpecificationModel()))
                            .findFirst()
@@ -702,13 +844,15 @@
                                salesLedgerProduct.setProductModelId(Long.parseLong(map.get("modelId").toString()));
                                salesLedgerProduct.setProductId(Long.parseLong(map.get("id").toString()));
                            });
                    // 填充登记信息
                    salesLedgerProduct.setRegister(loginUser.getNickName());
                    salesLedgerProduct.setRegisterDate(LocalDateTime.now());
                    salesLedgerProduct.setApproveStatus(0);
                    salesLedgerProduct.setPendingTicketsTotal(salesLedgerProductImportDto.getTaxInclusiveTotalPrice());
                    // 是否质检判断
                    salesLedgerProduct.setIsChecked(salesLedgerProductImportDto.getIsChecked() == 1);
                    if(salesLedgerProductImportDto.getIsChecked() == 1){
                    salesLedgerProduct.setIsChecked(salesLedgerProductImportDto.getIsChecked() != null && salesLedgerProductImportDto.getIsChecked() == 1);
                    if(salesLedgerProduct.getIsChecked()){
                        addQualityInspect(salesLedger, salesLedgerProduct);
                    }
                    salesLedgerProductMapper.insert(salesLedgerProduct);
@@ -719,9 +863,35 @@
            return AjaxResult.success("导入成功");
        } catch (Exception e) {
            e.printStackTrace();
            log.error("导入失败:", e);
            throw new RuntimeException("导入数据过程中发生了错误:" + e.getMessage());
        }
        return AjaxResult.success("导入失败");
    }
    @Override
    public PurchaseLedgerDto getPurchaseByCode(PurchaseLedgerDto purchaseLedgerDto) {
        // 1. 查询主表
        PurchaseLedger purchaseLedger = purchaseLedgerMapper.selectOne(new LambdaQueryWrapper<PurchaseLedger>()
                .eq(PurchaseLedger::getPurchaseContractNumber, purchaseLedgerDto.getPurchaseContractNumber())
                .last("LIMIT 1"));
        if (purchaseLedger == null) {
            throw new BaseException("采购台账不存在");
        }
        // 2. 查询子表
        LambdaQueryWrapper<SalesLedgerProduct> productWrapper = new LambdaQueryWrapper<>();
        productWrapper.eq(SalesLedgerProduct::getSalesLedgerId, purchaseLedger.getId())
                .eq(SalesLedgerProduct::getType, 2);
        List<SalesLedgerProduct> products = salesLedgerProductMapper.selectList(productWrapper);
        // 4. 转换 DTO
        PurchaseLedgerDto resultDto = new PurchaseLedgerDto();
        BeanUtils.copyProperties(purchaseLedger, resultDto);
        if (!products.isEmpty()) {
            resultDto.setHasChildren(true);
            resultDto.setProductData(products);
        }
        return resultDto;
    }
    public void addApproveByPurchase(LoginUser loginUser,PurchaseLedger purchaseLedger) throws Exception {