供应商导入

This commit is contained in:
zjf committed 2025-02-28 15:28:20 +08:00
1 parent 45fa3999e1
commit 6b43728385
6 files changed
+267 -5

No files matched your search

@@ -33,7 +33,7 @@ public class SmErpSupplierImportDto {
@ExcelProperty("开户行及帐号")
private String bankAccount;
@ExcelProperty("货商类别")
@ExcelProperty("货商类")
private String supplierCategory;
@ExcelProperty("货商地区")
@@ -42,8 +42,8 @@ public class SmErpSupplierImportDto {
@ExcelProperty("建档人")
private String creator;
@ExcelProperty("状态")
private String status;
// @ExcelProperty("状态")
// private String status;
@ExcelProperty("期初应付款")
private Double initialPayable;
@@ -81,7 +81,7 @@ public class SmErpSupplierEntity extends Model<SmErpSupplierEntity> {
* 货商类别
*/
@Schema(description="货商类别")
private String supplierType;
private Long supplierType;
/**
* 货商地区
@@ -0,0 +1,22 @@
package com.bsd.pjcloud.supermarket.validarot;
import com.bsd.pjcloud.supermarket.dto.supplier.SmErpSupplierImportDto;
import org.springframework.stereotype.Component;
import java.util.ArrayList;
import java.util.List;
public class SupplierValidator {
public static List<String> validate(SmErpSupplierImportDto entity, int rowIndex) {
List<String> errors = new ArrayList<>();
if (entity.getSupplierName() == null || entity.getSupplierName().isEmpty()) {
errors.add("第" + (rowIndex + 1) + "行: 货商名称不能为空");
}
// if (entity.getPhone()== null || entity.getPhone().isEmpty()) {
// errors.add("第" + (rowIndex + 1) + "行: 电话不能为空");
// }
return errors;
}
}
@@ -6,10 +6,14 @@ import cn.hutool.core.collection.CollUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.bsd.pjcloud.admin.api.vo.UserExcelVO;
import com.bsd.pjcloud.common.core.util.BeanUtils;
import com.bsd.pjcloud.common.core.util.R;
import com.bsd.pjcloud.common.excel.annotation.RequestExcel;
import com.bsd.pjcloud.common.log.annotation.SysLog;
import com.bsd.pjcloud.common.security.annotation.HasPermission;
import com.bsd.pjcloud.common.security.util.SecurityUtils;
import com.bsd.pjcloud.supermarket.dto.supplier.SmErpSupplierImportDto;
import com.bsd.pjcloud.supermarket.entity.SmErpSupplierEntity;
import com.bsd.pjcloud.supermarket.service.SmErpSupplierService;
import com.bsd.pjcloud.supermarket.vo.erp.SmErpSupplierSimpleVo;
@@ -21,6 +25,7 @@ import org.springframework.http.HttpHeaders;
import io.swagger.v3.oas.annotations.tags.Tag;
import io.swagger.v3.oas.annotations.Operation;
import lombok.RequiredArgsConstructor;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.*;
import java.util.List;
@@ -135,4 +140,17 @@ public class SmErpSupplierController {
List<SmErpSupplierSimpleVo> bean = BeanUtils.toBean(list, SmErpSupplierSimpleVo.class);
return R.ok(bean);
}
/**
* 导入
*
* @param smErpSupplierImportDtos 用户列表
* @param bindingResult 错误信息列表
* @return R
*/
@PostMapping("/import")
// @PreAuthorize("@pms.hasPermission('supermarketerp_smErpSupplier_import')" )
public R importUser(@RequestExcel List<SmErpSupplierImportDto> smErpSupplierImportDtos, BindingResult bindingResult) {
return smErpSupplierService.importSupplier(smErpSupplierImportDtos, bindingResult);
}
}
@@ -3,7 +3,10 @@ package com.bsd.pjcloud.supermarket.service;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.IService;
import com.bsd.pjcloud.common.core.util.R;
import com.bsd.pjcloud.supermarket.dto.supplier.SmErpSupplierImportDto;
import com.bsd.pjcloud.supermarket.entity.SmErpSupplierEntity;
import org.springframework.validation.BindingResult;
import java.util.List;
@@ -24,4 +27,13 @@ public interface SmErpSupplierService extends IService<SmErpSupplierEntity> {
* @return
*/
Object pageScope(Page page, LambdaQueryWrapper<SmErpSupplierEntity> wrapper);
/**
* 导入
* @param smErpSupplierImportDtos
* @param bindingResult
* @return
*/
R importSupplier(List<SmErpSupplierImportDto> smErpSupplierImportDtos, BindingResult bindingResult);
}
@@ -1,15 +1,29 @@
package com.bsd.pjcloud.supermarket.service.impl;
import cn.hutool.core.lang.Assert;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.bsd.pjcloud.common.core.util.BeanUtils;
import com.bsd.pjcloud.common.core.util.R;
import com.bsd.pjcloud.common.data.datascope.DataScope;
import com.bsd.pjcloud.common.security.util.SecurityUtils;
import com.bsd.pjcloud.supermarket.dto.supplier.SmErpSupplierImportDto;
import com.bsd.pjcloud.supermarket.entity.SmErpSupplierEntity;
import com.bsd.pjcloud.supermarket.entity.SmErpSupplierTypeEntity;
import com.bsd.pjcloud.supermarket.mapper.SmErpSupplierMapper;
import com.bsd.pjcloud.supermarket.mapper.SmErpSupplierTypeMapper;
import com.bsd.pjcloud.supermarket.service.SmErpSupplierService;
import com.bsd.pjcloud.supermarket.validarot.SupplierValidator;
import lombok.AllArgsConstructor;
import org.springframework.dao.DuplicateKeyException;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;
import org.springframework.validation.BindingResult;
import java.util.List;
import java.util.*;
/**
* 货商管理
@@ -18,7 +32,10 @@ import java.util.List;
* @date 2024-12-20 12:07:42
*/
@Service
@AllArgsConstructor
public class SmErpSupplierServiceImpl extends ServiceImpl<SmErpSupplierMapper, SmErpSupplierEntity> implements SmErpSupplierService {
private final SmErpSupplierTypeMapper supplierTypeMapper;
@Override
public List<SmErpSupplierEntity> selectSimpleAllScope() {
return baseMapper.selectListByScope(new LambdaQueryWrapper<SmErpSupplierEntity>().eq(SmErpSupplierEntity::getStatus, "0"), DataScope.of());
@@ -28,4 +45,197 @@ public class SmErpSupplierServiceImpl extends ServiceImpl<SmErpSupplierMapper, S
public Object pageScope(Page page, LambdaQueryWrapper<SmErpSupplierEntity> wrapper) {
return baseMapper.selectPageByScope(page, wrapper, DataScope.of());
}
/* @Override
@Transactional
public R importSupplier(List<SmErpSupplierImportDto> smErpSupplierImportDtos, BindingResult bindingResult) {
if (smErpSupplierImportDtos.isEmpty()) {
return R.failed("导入内容为空");
}
List<R> result = new ArrayList<>();
for (int i = 0; i < smErpSupplierImportDtos.size(); i++) {
SmErpSupplierImportDto entity = smErpSupplierImportDtos.get(i);
List<String> errors = SupplierValidator.validate(entity, i);
if (!errors.isEmpty()) {
for (String error : errors) {
bindingResult.rejectValue("", "", error);
}
continue;
}
SmErpSupplierEntity supplier = BeanUtils.toBean(entity, SmErpSupplierEntity.class);
//查询货商
List<SmErpSupplierEntity> smErpSupplierEntities = baseMapper.selectListByScope(new LambdaQueryWrapper<>(SmErpSupplierEntity.class)
.eq(SmErpSupplierEntity::getSupplierName, supplier.getSupplierName()), DataScope.of());
//查询货商类型
String supplierCategory = entity.getSupplierCategory();
List<SmErpSupplierTypeEntity> smErpSupplierTypeEntities = supplierTypeMapper.selectListByScope(new LambdaQueryWrapper<>(SmErpSupplierTypeEntity.class)
.eq(SmErpSupplierTypeEntity::getTypeName, supplierCategory), DataScope.of());
Long supplierTypeId = determineSupplierTypeId(supplierCategory, smErpSupplierTypeEntities);
supplier.setSupplierId(supplierTypeId);
//如果有当前名称,则更新
if (CollectionUtils.isEmpty(smErpSupplierEntities)) {
boolean b = updateById(supplier);
if (b) {
result.add(R.ok("更新成功"));
} else {
result.add(R.failed("更新失败"));
}
} else {
boolean save = save(supplier);
if (save) {
result.add(R.ok("新增成功"));
} else {
result.add(R.ok("新增失败"));
}
}
}
return R.ok(result);
}
// 新增的公共方法
private Long determineSupplierTypeId(String category, List<SmErpSupplierTypeEntity> typeEntities) {
if (CollectionUtils.isEmpty(typeEntities)) {
SmErpSupplierTypeEntity newType = new SmErpSupplierTypeEntity();
newType.setTypeName(category);
supplierTypeMapper.insert(newType);
return newType.getId();
}
// 显式断言确保集合非空
Assert.notEmpty(typeEntities, "供应商类型查询结果不应为空");
return typeEntities.get(0).getId();
}
*/
@Override
@Transactional
public R importSupplier(List<SmErpSupplierImportDto> smErpSupplierImportDtos, BindingResult bindingResult) {
if (CollectionUtils.isEmpty(smErpSupplierImportDtos)) {
return R.failed("导入数据不能为空");
}
List<Map<String, Object>> errorList = new ArrayList<>();
List<SmErpSupplierEntity> successList = new ArrayList<>();
for (int i = 0; i < smErpSupplierImportDtos.size(); i++) {
int rowNumber = i + 1;
SmErpSupplierImportDto dto = smErpSupplierImportDtos.get(i);
List<String> errorReasons = new ArrayList<>();
// 数据校验阶段
List<String> validationErrors = SupplierValidator.validate(dto, rowNumber);
if (!validationErrors.isEmpty()) {
errorList.add(createErrorInfo(rowNumber, dto.getSupplierName(), validationErrors));
continue;
}
try {
// 处理供应商类型
SmErpSupplierTypeEntity typeEntity = resolveSupplierType(dto.getSupplierCategory());
if (typeEntity == null) {
errorReasons.add("供应商类型不存在且创建失败");
errorList.add(createErrorInfo(rowNumber, dto.getSupplierName(), errorReasons));
continue;
}
// 转换实体
SmErpSupplierEntity supplier = BeanUtils.toBean(dto, SmErpSupplierEntity.class);
supplier.setDeptId(SecurityUtils.getUser().getDeptId());
supplier.setSupplierType(typeEntity.getId());
// 根据名称检查存在性(需确保supplier_name有唯一约束)
SmErpSupplierEntity existing = getExistingSupplier(supplier.getSupplierName());
boolean operationResult;
if (existing != null) {
// 更新逻辑:保持原有ID
supplier.setSupplierId(existing.getSupplierId());
operationResult = updateById(supplier);
} else {
// 新增逻辑
operationResult = save(supplier);
}
if (operationResult) {
successList.add(supplier);
} else {
errorReasons.add(existing != null ? "更新失败" : "新增失败");
errorList.add(createErrorInfo(rowNumber, dto.getSupplierName(), errorReasons));
}
} catch (DuplicateKeyException e) {
errorReasons.add("供应商名称已存在");
errorList.add(createErrorInfo(rowNumber, dto.getSupplierName(), errorReasons));
} catch (Exception e) {
errorReasons.add("系统异常: " + e.getMessage());
errorList.add(createErrorInfo(rowNumber, dto.getSupplierName(), errorReasons));
}
}
return buildFinalResult(smErpSupplierImportDtos.size(), successList.size(), errorList);
}
// 辅助方法:获取已存在的供应商
private SmErpSupplierEntity getExistingSupplier(String supplierName) {
List<SmErpSupplierEntity> list = baseMapper.selectListByScope(
new LambdaQueryWrapper<SmErpSupplierEntity>()
.eq(SmErpSupplierEntity::getSupplierName, supplierName)
.last("LIMIT 1"),
DataScope.of()
);
return CollectionUtils.isEmpty(list) ? null : list.get(0);
}
// 构建最终返回结果
private R buildFinalResult(int total, int successCount, List<Map<String, Object>> errorList) {
Map<String, Object> result = new LinkedHashMap<>();
result.put("total", total);
result.put("successCount", successCount);
result.put("errorCount", errorList.size());
if (!errorList.isEmpty()) {
result.put("errors", errorList);
return R.failed( result,"部分数据导入失败");
}
return R.ok( result,"成功导入所有" + successCount + "条数据");
}
// 类型解析方法(带事务传播调整)
@Transactional(propagation = Propagation.REQUIRES_NEW) // 新事务避免主事务回滚影响
public SmErpSupplierTypeEntity resolveSupplierType(String typeName) {
// 先尝试查询
SmErpSupplierTypeEntity type = supplierTypeMapper.selectOne(
new LambdaQueryWrapper<SmErpSupplierTypeEntity>()
.eq(SmErpSupplierTypeEntity::getTypeName, typeName)
);
if (type != null) return type;
// 不存在则尝试插入
try {
SmErpSupplierTypeEntity newType = new SmErpSupplierTypeEntity();
newType.setTypeName(typeName);
if (supplierTypeMapper.insert(newType) > 0) {
return newType;
}
} catch (DuplicateKeyException e) {
// 并发情况下其他事务已创建
return supplierTypeMapper.selectOne(
new LambdaQueryWrapper<SmErpSupplierTypeEntity>()
.eq(SmErpSupplierTypeEntity::getTypeName, typeName)
);
}
return null;
}
// 错误信息构建方法
private Map<String, Object> createErrorInfo(int row, String name, List<String> reasons) {
return new HashMap<String, Object>() {{
put("row", row);
put("supplierName", name);
put("reasons", reasons);
}};
}
}