From bf2026a38d4d36371060673d4651b6e05ca90632 Mon Sep 17 00:00:00 2001
From: liding <756868258@qq.com>
Date: 星期二, 01 九月 2026 17:07:30 +0800
Subject: [PATCH] feat(device): 1.更新设备导入验证逻辑和检验任务功能 2.报告编制
---
cnas-device/src/main/java/com/ruoyi/device/service/impl/DeviceServiceImpl.java | 205 +++++++++++++++++++++++++++++++++++++++++++++++++-
1 files changed, 198 insertions(+), 7 deletions(-)
diff --git a/cnas-device/src/main/java/com/ruoyi/device/service/impl/DeviceServiceImpl.java b/cnas-device/src/main/java/com/ruoyi/device/service/impl/DeviceServiceImpl.java
index 99bbc0b..a58e4be 100644
--- a/cnas-device/src/main/java/com/ruoyi/device/service/impl/DeviceServiceImpl.java
+++ b/cnas-device/src/main/java/com/ruoyi/device/service/impl/DeviceServiceImpl.java
@@ -2,6 +2,7 @@
import cn.hutool.core.util.StrUtil;
import cn.hutool.json.JSONObject;
+import com.alibaba.excel.EasyExcel;
import com.alibaba.fastjson2.JSON;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
@@ -15,9 +16,12 @@
import com.ruoyi.basic.mapper.StructureItemParameterMapper;
import com.ruoyi.basic.pojo.StructureItemParameter;
import com.ruoyi.common.core.domain.Result;
+import com.ruoyi.common.core.domain.entity.SysDictData;
+import com.ruoyi.common.core.domain.entity.SysDept;
import com.ruoyi.common.core.domain.entity.User;
import com.ruoyi.common.utils.QueryWrappers;
import com.ruoyi.device.dto.*;
+import com.ruoyi.device.excel.upload.DeviceImport;
import com.ruoyi.device.mapper.CollectBridgeMapper;
import com.ruoyi.device.mapper.DeviceMaintenanceMapper;
import com.ruoyi.device.mapper.DeviceMapper;
@@ -31,6 +35,8 @@
import com.ruoyi.inspect.mapper.InsSampleMapper;
import com.ruoyi.inspect.pojo.InsProduct;
import com.ruoyi.inspect.util.HackLoopTableRenderPolicy;
+import com.ruoyi.system.mapper.SysDictDataMapper;
+import com.ruoyi.system.mapper.SysDeptMapper;
import com.ruoyi.system.mapper.UserMapper;
import lombok.AllArgsConstructor;
import org.apache.logging.log4j.util.Strings;
@@ -42,8 +48,10 @@
import javax.servlet.http.HttpServletResponse;
import java.io.InputStream;
import java.io.OutputStream;
+import java.math.BigDecimal;
import java.net.URLEncoder;
import java.text.SimpleDateFormat;
+import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.*;
@@ -59,6 +67,10 @@
private DeviceMapper deviceMapper;
private UserMapper userMapper;
+
+ private SysDeptMapper sysDeptMapper;
+
+ private SysDictDataMapper sysDictDataMapper;
private StructureItemParameterMapper structureItemParameterMapper;
@@ -93,10 +105,6 @@
@Transactional(rollbackFor = Exception.class)
@Override
public int upDeviceParameter(Device itemParameter) {
- // 鍒犻櫎鏁伴噰闆嗛厤缃暟鎹�
- dataConfigService.deleteDataConfig();
- // 闇�瑕佸悓鏃舵洿鏀� device琛�
-
return deviceMapper.updateById(itemParameter);
}
@@ -356,6 +364,7 @@
template.write(os);
os.flush();
os.close();
+ inputStream.close();
} catch (Exception e) {
e.printStackTrace();
throw new RuntimeException("瀵煎嚭澶辫触");
@@ -400,11 +409,11 @@
DeviceMaintenance deviceMaintenance = deviceMaintenanceList.get(i);
DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
// 缁翠慨鏃ユ湡
- deviceMetricRecordAndMaintenanceDto.setMaintenanceDateString(deviceMaintenance.getDate().format(dateTimeFormatter));
+ deviceMetricRecordAndMaintenanceDto.setMaintenanceDateString(deviceMaintenance.getMaintenanceDate().format(dateTimeFormatter));
// 澶勭悊鏂规硶
- deviceMetricRecordAndMaintenanceDto.setHandlingMethod(deviceMaintenance.getContent());
+ deviceMetricRecordAndMaintenanceDto.setHandlingMethod(deviceMaintenance.getMaintenanceContent());
// 澶囨敞
- deviceMetricRecordAndMaintenanceDto.setComments(deviceMaintenance.getComments());
+ deviceMetricRecordAndMaintenanceDto.setComments(deviceMaintenance.getRemark());
}
deviceMetricRecordAndMaintenanceDtoList.add(deviceMetricRecordAndMaintenanceDto);
@@ -491,9 +500,191 @@
template.write(os);
os.flush();
os.close();
+ inputStream.close();
} catch (Exception e) {
e.printStackTrace();
throw new RuntimeException("瀵煎嚭澶辫触");
}
}
+
+ @Override
+ public void downloadImportTemplate(HttpServletResponse response) {
+ response.reset();
+ response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
+ response.setHeader("Access-Control-Expose-Headers", "Content-Disposition");
+ try {
+ String fileName = URLEncoder.encode("璁惧瀵煎叆妯℃澘.xlsx", "UTF-8");
+ response.setHeader("Content-Disposition", "attachment;filename=" + fileName);
+ EasyExcel.write(response.getOutputStream(), DeviceImport.class)
+ .sheet("璁惧瀵煎叆妯℃澘")
+ .doWrite(Collections.emptyList());
+ } catch (Exception e) {
+ throw new RuntimeException("璁惧瀵煎叆妯℃澘涓嬭浇澶辫触", e);
+ }
+ }
+
+ @Override
+ @Transactional(rollbackFor = Exception.class)
+ public int importDevice(org.springframework.web.multipart.MultipartFile file) {
+ if (file == null || file.isEmpty()) {
+ throw new RuntimeException("璇烽�夋嫨闇�瑕佸鍏ョ殑Excel鏂囦欢");
+ }
+ String fileName = file.getOriginalFilename();
+ if (fileName == null || !fileName.toLowerCase(Locale.ROOT).endsWith(".xlsx")) {
+ throw new RuntimeException("浠呮敮鎸�.xlsx鏍煎紡鏂囦欢");
+ }
+
+ final List<DeviceImport> rows;
+ try {
+ rows = EasyExcel.read(file.getInputStream())
+ .head(DeviceImport.class)
+ .sheet()
+ .doReadSync();
+ } catch (Exception e) {
+ throw new RuntimeException("Excel瑙f瀽澶辫触锛岃浣跨敤涓嬭浇鐨勫鍏ユā鏉�", e);
+ }
+ if (CollectionUtils.isEmpty(rows)) {
+ throw new RuntimeException("瀵煎叆鏂囦欢娌℃湁璁惧鏁版嵁");
+ }
+
+ Set<String> fileKeys = new HashSet<>();
+ for (int i = 0; i < rows.size(); i++) {
+ String managementNumber = required(rows.get(i).getManagementNumber(), i + 2, "绠$悊缂栧彿");
+ String deviceName = required(rows.get(i).getDeviceName(), i + 2, "浠櫒鍚嶇О");
+ String specificationModel = required(rows.get(i).getSpecificationModel(), i + 2, "瑙勬牸鍨嬪彿");
+ if (!fileKeys.add(deviceKey(deviceName, specificationModel, managementNumber))) {
+ throw new RuntimeException("绗�" + (i + 2) + "琛岋細浠櫒鍚嶇О+瑙勬牸鍨嬪彿+绠$悊缂栧彿鍦ㄦ枃浠朵腑閲嶅");
+ }
+ }
+ Set<String> existingKeys = baseMapper.selectList(Wrappers.<Device>lambdaQuery()
+ .select(Device::getDeviceName, Device::getSpecificationModel, Device::getManagementNumber))
+ .stream().map(d -> deviceKey(d.getDeviceName(), d.getSpecificationModel(), d.getManagementNumber())).collect(Collectors.toSet());
+
+ Map<String, List<SysDept>> departmentMap = sysDeptMapper.selectDeptList(new SysDept()).stream()
+ .filter(item -> StringUtils.isNotBlank(item.getDeptName()))
+ .collect(Collectors.groupingBy(item -> item.getDeptName().trim()));
+ Map<String, List<User>> userMap = userMapper.selectList(Wrappers.<User>lambdaQuery()
+ .isNotNull(User::getName).select(User::getId, User::getName))
+ .stream().collect(Collectors.groupingBy(item -> item.getName().trim()));
+ Map<String, String> statusMap = dictMap("device_status");
+ Map<String, String> typeMap = dictMap("device_type");
+
+ List<Device> devices = new ArrayList<>();
+ for (int i = 0; i < rows.size(); i++) {
+ int rowNumber = i + 2;
+ DeviceImport row = rows.get(i);
+ String managementNumber = required(row.getManagementNumber(), rowNumber, "绠$悊缂栧彿");
+ String deviceName = required(row.getDeviceName(), rowNumber, "浠櫒鍚嶇О");
+ String specificationModel = required(row.getSpecificationModel(), rowNumber, "瑙勬牸鍨嬪彿");
+ if (existingKeys.contains(deviceKey(deviceName, specificationModel, managementNumber))) {
+ throw new RuntimeException("绗�" + rowNumber + "琛岋細浠櫒鍚嶇О鈥�" + deviceName + "鈥�+瑙勬牸鍨嬪彿鈥�" + specificationModel + "鈥�+绠$悊缂栧彿鈥�" + managementNumber + "鈥濆凡瀛樺湪");
+ }
+
+ String laboratoryName = required(row.getLaboratoryName(), rowNumber, "鎵�灞為儴闂�");
+ List<SysDept> departments = departmentMap.get(laboratoryName);
+ if (CollectionUtils.isEmpty(departments) || departments.size() > 1) {
+ throw new RuntimeException("绗�" + rowNumber + "琛岋細鎵�灞為儴闂ㄢ��" + laboratoryName + "鈥濅笉瀛樺湪鎴栦笉鍞竴");
+ }
+
+ Device device = new Device();
+ device.setDeviceName(deviceName);
+ device.setSpecificationModel(specificationModel);
+ device.setManagementNumber(managementNumber);
+ device.setActivationDate(parseDate(row.getActivationDate()));
+ device.setSubordinateDepartmentsId(departments.get(0).getDeptId().intValue());
+ device.setDeviceStatus(Integer.valueOf(dictValue(statusMap, row.getDeviceStatus(), rowNumber, "褰撳墠鐘舵��", true)));
+ device.setCalibrationDate(required(row.getCalibrationDate(), rowNumber, "鏍″噯鍛ㄦ湡(鏈�)"));
+ device.setEnDeviceName(trim(row.getEnDeviceName()));
+ device.setManufacturer(trim(row.getManufacturer()));
+ device.setFactoryNo(trim(row.getFactoryNo()));
+ device.setAssetCode(trim(row.getAssetCode()));
+ device.setOrigin(trim(row.getOrigin()));
+ device.setAcquisitionDate(parseDate(row.getAcquisitionDate()));
+ device.setStoragePoint(trim(row.getStoragePoint()));
+ device.setTechnicalIndicators(trim(row.getTechnicalIndicators()));
+ device.setCalibrationServices(trim(row.getCalibrationServices()));
+ device.setLastCalibrationDate(parseDate(row.getLastCalibrationDate()));
+ device.setNextCalibrationDate(parseDate(row.getNextCalibrationDate()));
+ device.setLargeCategory(dictValue(typeMap, row.getLargeCategory(), rowNumber, "璁惧绫诲瀷", false));
+ device.setUnitPrice(parseDecimal(row.getUnitPrice(), rowNumber, "鍗曚环(涓囧厓)"));
+
+ String managerName = trim(row.getEquipmentManagerName());
+ if (StringUtils.isNotBlank(managerName)) {
+ List<User> users = userMap.get(managerName);
+ if (CollectionUtils.isEmpty(users) || users.size() > 1) {
+ throw new RuntimeException("绗�" + rowNumber + "琛岋細璐熻矗浜衡��" + managerName + "鈥濅笉瀛樺湪鎴栦笉鍞竴");
+ }
+ device.setEquipmentManager(users.get(0).getId());
+ }
+ devices.add(device);
+ }
+ saveBatch(devices);
+ return devices.size();
+ }
+
+ private Map<String, String> dictMap(String dictType) {
+ return sysDictDataMapper.selectDictDataByType(dictType).stream()
+ .collect(Collectors.toMap(item -> item.getDictLabel().trim(), SysDictData::getDictValue, (first, second) -> first));
+ }
+
+ private String dictValue(Map<String, String> values, String input, int rowNumber, String column, boolean required) {
+ String text = trim(input);
+ if (StringUtils.isBlank(text)) {
+ if (required) {
+ throw new RuntimeException("绗�" + rowNumber + "琛岋細" + column + "涓嶈兘涓虹┖");
+ }
+ return null;
+ }
+ String value = values.get(text);
+ if (value == null && values.containsValue(text)) {
+ value = text;
+ }
+ if (value == null) {
+ throw new RuntimeException("绗�" + rowNumber + "琛岋細" + column + "鈥�" + text + "鈥濅笉鍦ㄧ郴缁熷瓧鍏镐腑");
+ }
+ return value;
+ }
+
+ private LocalDateTime parseDate(String input) {
+ String text = trim(input);
+ if (StringUtils.isBlank(text)) {
+ return null;
+ }
+ String datePart = text.replace('/', '-').split("\\s+")[0];
+ try {
+ return LocalDate.parse(datePart, DateTimeFormatter.ofPattern("yyyy-M-d")).atStartOfDay();
+ } catch (Exception e) {
+ return null;
+ }
+ }
+
+ private BigDecimal parseDecimal(String input, int rowNumber, String column) {
+ String text = trim(input);
+ if (StringUtils.isBlank(text)) {
+ return null;
+ }
+ try {
+ return new BigDecimal(text);
+ } catch (NumberFormatException e) {
+ throw new RuntimeException("绗�" + rowNumber + "琛岋細" + column + "蹇呴』鏄暟瀛�", e);
+ }
+ }
+
+ private String required(String input, int rowNumber, String column) {
+ String value = trim(input);
+ if (StringUtils.isBlank(value)) {
+ throw new RuntimeException("绗�" + rowNumber + "琛岋細" + column + "涓嶈兘涓虹┖");
+ }
+ return value;
+ }
+
+ private String deviceKey(String deviceName, String specificationModel, String managementNumber) {
+ return (deviceName == null ? "" : deviceName.trim()) + "|"
+ + (specificationModel == null ? "" : specificationModel.trim()) + "|"
+ + (managementNumber == null ? "" : managementNumber.trim());
+ }
+
+ private String trim(String value) {
+ return value == null ? null : value.trim();
+ }
}
--
Gitblit v1.9.3