liyong
2026-04-24 c1bbff15e4f64767d471de763613a54c9cb8d4b4
src/main/java/com/ruoyi/sales/service/impl/SalesLedgerServiceImpl.java
@@ -19,12 +19,13 @@
import com.deepoove.poi.plugin.table.LoopRowTableRenderPolicy;
import com.ruoyi.account.service.AccountIncomeService;
import com.ruoyi.basic.dto.CustomerPrivatePoolDto;
import com.ruoyi.basic.dto.ProductModelAnticlockwiseDto;
import com.ruoyi.basic.mapper.CustomerMapper;
import com.ruoyi.basic.mapper.CustomerPrivatePoolMapper;
import com.ruoyi.basic.mapper.ProductMapper;
import com.ruoyi.basic.mapper.ProductModelMapper;
import com.ruoyi.basic.pojo.Customer;
import com.ruoyi.basic.pojo.CustomerPrivatePool;
import com.ruoyi.basic.service.IProductModelService;
import com.ruoyi.common.enums.FileNameType;
import com.ruoyi.common.enums.SaleEnum;
import com.ruoyi.common.exception.base.BaseException;
@@ -37,13 +38,12 @@
import com.ruoyi.framework.web.domain.AjaxResult;
import com.ruoyi.other.mapper.TempFileMapper;
import com.ruoyi.other.pojo.TempFile;
import com.ruoyi.production.mapper.*;
import com.ruoyi.production.mapper.ProductStructureMapper;
import com.ruoyi.production.service.ProductionProductMainService;
import com.ruoyi.project.system.domain.SysDept;
import com.ruoyi.project.system.domain.SysUser;
import com.ruoyi.project.system.mapper.SysDeptMapper;
import com.ruoyi.project.system.mapper.SysUserMapper;
import com.ruoyi.quality.mapper.QualityInspectMapper;
import com.ruoyi.sales.dto.*;
import com.ruoyi.sales.mapper.*;
import com.ruoyi.sales.pojo.*;
@@ -134,6 +134,8 @@
    private SysUserMapper sysUserMapper;
    @Autowired
    private CustomerPrivatePoolMapper customerPrivatePoolMapper;
    @Autowired
    private IProductModelService productModelService;
    @Override
    public List<SalesLedger> selectSalesLedgerList(SalesLedgerDto salesLedgerDto) {
@@ -529,6 +531,141 @@
        exportProcessContractToWord(exportProcessContract);
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public AjaxResult importSalsesLedger(MultipartFile file) {
        LoginUser loginUser = SecurityUtils.getLoginUser();
        int successCount = 0;
        Date lastDate = null;
        BigDecimal lastUnitPrice = null;
        int skipCount = 0;
        List<String> errorMessages = new ArrayList<>();
        CustomerPrivatePoolDto lastCustomer = null;
        try {
            InputStream inputStream = file.getInputStream();
            ExcelUtil<SalesLedgerSimpleImportDto> excelUtil = new ExcelUtil<>(SalesLedgerSimpleImportDto.class);
            List<SalesLedgerSimpleImportDto> importDataList = excelUtil.importExcel(inputStream);
            if (CollectionUtils.isEmpty(importDataList)) {
                return AjaxResult.error("导入数据为空!");
            }
            List<String> customerNames = importDataList.stream()
                    .map(SalesLedgerSimpleImportDto::getCustomerName)
                    .filter(StrUtil::isNotBlank)
                    .distinct()
                    .collect(Collectors.toList());
            List<CustomerPrivatePoolDto> customers = customerPrivatePoolMapper.selectByCusterNames(customerNames);
            for (int i = 0; i < importDataList.size(); i++) {
                SalesLedgerSimpleImportDto importDto = importDataList.get(i);
                int rowNum = i + 2;
                if (StrUtil.isBlank(importDto.getOrderNo())) {
                    errorMessages.add(String.format("第%d行:订单编号为空", rowNum));
                    skipCount++;
                    continue;
                }
                if (importDto.getQuantity() == null ) {
                    errorMessages.add(String.format("第%d行:数量不能为空", rowNum));
                    skipCount++;
                    continue;
                }
                long count = salesLedgerMapper.selectCount(new LambdaQueryWrapper<SalesLedger>()
                        .eq(SalesLedger::getSalesContractNo, importDto.getOrderNo()));
                if (count > 0) {
                    errorMessages.add(String.format("第%d行:订单编号[%s]已存在", rowNum, importDto.getOrderNo()));
                    skipCount++;
                    continue;
                }
                CustomerPrivatePoolDto matchedCustomer = customers.stream()
                        .filter(c -> c.getCustomerName().equals(importDto.getCustomerName()))
                        .findFirst()
                        .orElse(lastCustomer);
                if (matchedCustomer == null) {
                    errorMessages.add(String.format("第%d行:客户[%s]不存在且无历史客户", rowNum, importDto.getCustomerName()));
                    skipCount++;
                    continue;
                }
                lastCustomer = matchedCustomer;
                try {
                    SalesLedger salesLedger = new SalesLedger();
                    salesLedger.setSalesContractNo(importDto.getOrderNo());
                    salesLedger.setCustomerName(matchedCustomer.getCustomerName());
                    salesLedger.setCustomerId(matchedCustomer.getCustomerId());
                    salesLedger.setCustomerContractNo(matchedCustomer.getTaxpayerIdentificationNumber());
                    Date date = importDto.getOrderDate();
                    if (ObjectUtils.isEmpty(date)){
                        date = lastDate;
                    }
                    lastDate = date;
                    salesLedger.setEntryDate(date);
                    salesLedger.setContractAmount(importDto.getAmount());
                    salesLedger.setEntryPerson(loginUser.getUserId().toString());
                    salesLedger.setTenantId(matchedCustomer.getTenantId());
                    salesLedgerMapper.insert(salesLedger);
                    SalesLedgerProduct product = new SalesLedgerProduct();
                    product.setSalesLedgerId(salesLedger.getId());
                    product.setType(1);
                    product.setQuantity(importDto.getQuantity());
                    BigDecimal unitPrice = importDto.getUnitPrice();
                    if (ObjectUtils.isEmpty(unitPrice)) {
                        unitPrice = lastUnitPrice;
                    }
                    lastUnitPrice = unitPrice;
                    product.setTaxInclusiveUnitPrice(unitPrice);
                    product.setTaxInclusiveTotalPrice(unitPrice.multiply(importDto.getQuantity()));
                    product.setTaxExclusiveTotalPrice(unitPrice.multiply(importDto.getQuantity()));
                    product.setNoInvoiceNum(importDto.getQuantity());
                    product.setNoInvoiceAmount(importDto.getAmount());
                    product.setPendingInvoiceTotal(importDto.getAmount());
                    product.setUnit("/");
                    product.setProductCategory(importDto.getProductName());
                    product.setSpecificationModel(importDto.getProductName());
                    product.setRegister(loginUser.getNickName());
                    product.setRegisterDate(LocalDateTime.now());
                    product.setApproveStatus(0);
                    if (ObjectUtils.isEmpty(product.getProductModelId())) {
                        ProductModelAnticlockwiseDto productModelAnticlockwiseDto = new ProductModelAnticlockwiseDto();
                        productModelAnticlockwiseDto.setModel(product.getSpecificationModel());
                        productModelAnticlockwiseDto.setProductName(product.getProductCategory());
                        productModelAnticlockwiseDto.setUnit("/");
                        productModelAnticlockwiseDto.setSubUnit("/");
                        Long productModelId = productModelService.productModelAnticlockwise(productModelAnticlockwiseDto);
                        product.setProductModelId(productModelId);
                    }
                    salesLedgerProductMapper.insert(product);
                    salesLedgerProductServiceImpl.addProductionData(product);
                    successCount++;
                } catch (Exception e) {
                    log.error("第{}行订单[{}]导入失败:{}", rowNum, importDto.getOrderNo(), e.getMessage(), e);
                    errorMessages.add(String.format("第%d行订单[%s]:导入失败-%s", rowNum, importDto.getOrderNo(), e.getMessage()));
                    skipCount++;
                }
            }
            String message = String.format("导入完成!成功%d条,跳过%d条", successCount, skipCount);
            if (!errorMessages.isEmpty()) {
                message += "。错误详情:" + String.join(";", errorMessages);
            }
            return AjaxResult.success(message);
        } catch (Exception e) {
            log.error("导入销售台账失败", e);
            throw new RuntimeException("导入失败:" + e.getMessage(), e);
        }
    }
    @SneakyThrows
    private void exportProcessContractToWord(@NotNull ExportProcessContractVo exportProcessContract) {
@@ -609,11 +746,12 @@
        List<Long> productIds = products.stream()
                .map(SalesLedgerProduct::getId)
                .collect(Collectors.toList());
        //删除生产数据
        salesLedgerProductServiceImpl.deleteProductionData(productIds);
        // 批量删除产品子表
        if (!productIds.isEmpty()) {
            //删除生产数据
            salesLedgerProductServiceImpl.deleteProductionData(productIds);
            salesLedgerProductMapper.deleteBatchIds(productIds);
        }
@@ -676,10 +814,15 @@
            SalesLedger salesLedger = convertToEntity(salesLedgerDto);
            salesLedger.setCustomerName(customer.getCustomerName());
            salesLedger.setTenantId(customer.getTenantId());
            // 3. 新增或更新主表
            if (salesLedger.getId() == null) {
                // 为空 自动生成
                String contractNo =StrUtil.isBlank(salesLedgerDto.getSalesContractNo())? generateSalesContractNoBy8Date():salesLedgerDto.getSalesContractNo();
                // 不能有重复数据的合同号
               Assert.isTrue(salesLedgerMapper.selectOne(new LambdaQueryWrapper<SalesLedger>()
                        .eq(SalesLedger::getSalesContractNo, contractNo)
                        .last("limit 1")) == null, contractNo+"合同号已存在");
                salesLedger.setSalesContractNo(contractNo);
                salesLedgerMapper.insert(salesLedger);
            } else {
@@ -689,6 +832,18 @@
            // 4. 处理子表数据
            List<SalesLedgerProduct> productList = salesLedgerDto.getProductData();
            for (SalesLedgerProduct product : productList) {
                //空的先新增基础数据  非空直接往下走
                if (ObjectUtils.isEmpty(product.getProductModelId())) {
                    ProductModelAnticlockwiseDto  productModelAnticlockwiseDto =  new ProductModelAnticlockwiseDto();
                    productModelAnticlockwiseDto.setModel(product.getSpecificationModel());
                    productModelAnticlockwiseDto.setProductName(product.getProductCategory());
                    productModelAnticlockwiseDto.setUnit(product.getUnit());
                    productModelAnticlockwiseDto.setSubUnit(product.getUnit());
                    Long productModelId = productModelService.productModelAnticlockwise(productModelAnticlockwiseDto);
                    product.setProductModelId(productModelId);
                }
            }
            if (productList != null && !productList.isEmpty()) {
                handleSalesLedgerProducts(salesLedger.getId(), productList, EnumUtil.fromCode(SaleEnum.class, salesLedgerDto.getType()));
                updateMainContractAmount(