Parcourir la source

新增设备基础信息、设备维护记录、设备状态、设备类别的增删改查功能

zlm il y a 7 mois
Parent
commit
f369e8a635
16 fichiers modifiés avec 1409 ajouts et 0 suppressions
  1. 78 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/domain/EquipmentBase.java
  2. 68 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/domain/EquipmentMaintain.java
  3. 75 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/domain/EquipmentStatus.java
  4. 39 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/domain/EquipmentType.java
  5. 11 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/mapper/EquipmentBaseMapper.java
  6. 9 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/mapper/EquipmentMaintainMapper.java
  7. 9 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/mapper/EquipmentStatusMapper.java
  8. 9 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/mapper/EquipmentTypeMapper.java
  9. 53 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/EquipmentBaseService.java
  10. 36 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/EquipmentMaintainService.java
  11. 34 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/EquipmentStatusService.java
  12. 49 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/EquipmentTypeService.java
  13. 224 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/impl/EquipmentBaseServiceImpl.java
  14. 134 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/impl/EquipmentMaintainServiceImpl.java
  15. 192 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/impl/EquipmentStatusServiceImpl.java
  16. 389 0
      pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/impl/EquipmentTypeServiceImpl.java

+ 78 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/domain/EquipmentBase.java

@@ -0,0 +1,78 @@
+package com.zksy.base.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import java.util.Date;
+
+/**
+ * 设备基础信息表
+ */
+@Data
+@AllArgsConstructor
+@NoArgsConstructor
+@TableName("equipment_base")
+public class EquipmentBase {
+
+    @TableId(value = "equipment_id", type = IdType.ASSIGN_UUID)
+    /**
+     * 设备唯一ID(主键)
+     */
+    private String equipmentId;
+
+    /**
+     * 设备编码(唯一标识)
+     */
+    private String equipmentCode;
+
+    /**
+     * 设备名称
+     */
+    private String equipmentName;
+
+    /**
+     * 设备型号
+     */
+    private String equipmentModel;
+
+    /**
+     * 设备规格参数
+     */
+    private String equipmentSpec;
+
+    /**
+     * 设备制造商
+     */
+    private String manufacturer;
+
+    /**
+     * 设备生产日期
+     */
+    @JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
+    private Date productionDate;
+
+    /**
+     * 设备类别ID(关联equipment_type表)
+     */
+    private String equipmentTypeId;
+
+    /**
+     * 设备资产价值(元)
+     */
+    private Double assetValue;
+
+    /**
+     * 预计使用年限(年)
+     */
+    private Integer useLife;
+
+    /**
+     * 备注信息
+     */
+    private String remark;
+}

+ 68 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/domain/EquipmentMaintain.java

@@ -0,0 +1,68 @@
+package com.zksy.base.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import java.util.Date;
+
+/**
+ * 设备维护记录表
+ */
+@TableName("equipment_maintain")
+@Data
+@AllArgsConstructor
+@NoArgsConstructor
+public class EquipmentMaintain {
+
+    @TableId(value = "maintain_id", type = IdType.ASSIGN_UUID)
+    /**
+     * 维护记录ID(主键)
+     */
+    private String maintainId;
+
+    /**
+     * 设备ID(关联equipment_base表)
+     */
+    private String equipmentId;
+
+    /**
+     * 维护类型(日常保养、故障维修、定期检测等)
+     */
+    private String maintainType;
+
+    /**
+     * 维护内容详情
+     */
+    private String maintainContent;
+
+    /**
+     * 维护人
+     */
+    private String maintainPerson;
+
+    /**
+     * 维护人联系方式
+     */
+    private Integer maintainPersonPhone;
+
+    /**
+     * 维护日期
+     */
+    @JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
+    private Date maintainDate;
+
+    /**
+     * 维护费用(元)
+     */
+    private Double maintainCost;
+
+    /**
+     * 维护备注信息
+     */
+    private String maintainRemark;
+}

+ 75 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/domain/EquipmentStatus.java

@@ -0,0 +1,75 @@
+package com.zksy.base.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+import java.time.LocalDateTime;
+import java.util.Date;
+
+/**
+ * 设备状态表
+ */
+@Data
+@AllArgsConstructor
+@NoArgsConstructor
+@TableName("equipment_status")
+public class EquipmentStatus {
+
+    @TableId(value = "status_id", type = IdType.ASSIGN_UUID)
+    /**
+     * 状态记录ID(主键)
+     */
+    private String statusId;
+
+    /**
+     * 设备ID(关联equipment_base表)
+     */
+    private String equipmentId;
+
+    /**
+     * 设备当前状态:1-在用,2-闲置,3-维修,4-报废,5-待入库
+     */
+    private Integer currentStatus;
+
+    /**
+     * 报警状态(0-正常,1-报警)
+     */
+    private Integer alarmStatus;
+
+    /**
+     * 在线状态(0-离线,1-在线)
+     */
+    private Integer onlineStatus;
+
+    /**
+     * 负责人ID(可关联用户表)
+     */
+    private Long userId;
+
+    /**
+     * 安装/存放地址
+     */
+    private String installationAddr;
+
+    /**
+     * 最后一次维护日期
+     */
+    @JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
+    private Date lastMaintainDate;
+
+    /**
+     * 下次预计维护日期
+     */
+    @JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
+    private Date nextMaintainDate;
+
+    /**
+     * 状态更新时间
+     */
+    private LocalDateTime statusUpdateTime;
+}

+ 39 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/domain/EquipmentType.java

@@ -0,0 +1,39 @@
+package com.zksy.base.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+/**
+ * 设备类别表
+ */
+@Data
+@AllArgsConstructor
+@NoArgsConstructor
+@TableName("equipment_type")
+public class EquipmentType {
+
+    @TableId(value = "type_id", type = IdType.ASSIGN_UUID)
+    /**
+     * 类别ID(主键)
+     */
+    private String typeId;
+
+    /**
+     * 类别名称(如生产设备、办公设备等)
+     */
+    private String typeName;
+
+    /**
+     * 父类别ID,用于多级分类,0表示无父类
+     */
+    private String parentTypeId;
+
+    /**
+     * 类别备注信息
+     */
+    private String typeRemark;
+}

+ 11 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/mapper/EquipmentBaseMapper.java

@@ -0,0 +1,11 @@
+package com.zksy.base.mapper;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.zksy.base.domain.EquipmentBase;
+import org.apache.ibatis.annotations.Mapper;
+
+@Mapper
+public interface EquipmentBaseMapper extends BaseMapper<EquipmentBase>{
+
+//    EquipmentBase getByIdTest(String id);
+}

+ 9 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/mapper/EquipmentMaintainMapper.java

@@ -0,0 +1,9 @@
+package com.zksy.base.mapper;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.zksy.base.domain.EquipmentMaintain;
+import org.apache.ibatis.annotations.Mapper;
+
+@Mapper
+public interface EquipmentMaintainMapper extends BaseMapper<EquipmentMaintain> {
+}

+ 9 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/mapper/EquipmentStatusMapper.java

@@ -0,0 +1,9 @@
+package com.zksy.base.mapper;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.zksy.base.domain.EquipmentStatus;
+import org.apache.ibatis.annotations.Mapper;
+
+@Mapper
+public interface EquipmentStatusMapper extends BaseMapper<EquipmentStatus> {
+}

+ 9 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/mapper/EquipmentTypeMapper.java

@@ -0,0 +1,9 @@
+package com.zksy.base.mapper;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.zksy.base.domain.EquipmentType;
+import org.apache.ibatis.annotations.Mapper;
+
+@Mapper
+public interface EquipmentTypeMapper extends BaseMapper<EquipmentType> {
+}

+ 53 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/EquipmentBaseService.java

@@ -0,0 +1,53 @@
+package com.zksy.base.service;
+
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.zksy.base.domain.EquipmentBase;
+import org.springframework.stereotype.Service;
+
+import java.util.List;
+
+@Service
+public interface EquipmentBaseService extends IService<EquipmentBase> {
+
+    Page<EquipmentBase> findByPage(long pageNum, long pageSize,
+                                   String equipmentCode,String equipmentName,
+                                   String equipmentModel,String manufacturer);
+
+    /**
+     * 新增仪器信息
+     * @param entity
+     * @return
+     */
+    boolean saveWithCheck(EquipmentBase entity);
+
+    /**
+     * 新增仪器信息
+     * @param entityList
+     * @return
+     */
+    boolean saveBatchWithCheck(List<EquipmentBase> entityList);
+
+    /**
+     * 修改仪器信息
+     * @param entity
+     * @return
+     */
+    boolean updateWithCheck(EquipmentBase entity);
+
+    /**
+     * 删除设备基础信息
+     * @param id
+     * @return
+     */
+    boolean removeWithCheck(String id);
+
+    /**
+     * 设备基础信息批量删除
+     * @param ids
+     * @return
+     */
+    boolean removeBatchWithCheck(List<String> ids);
+
+//    EquipmentBase getByIdTest(String id);
+}

+ 36 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/EquipmentMaintainService.java

@@ -0,0 +1,36 @@
+package com.zksy.base.service;
+
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.zksy.base.domain.EquipmentMaintain;
+import org.springframework.stereotype.Service;
+
+import java.util.List;
+
+@Service
+public interface EquipmentMaintainService extends IService<EquipmentMaintain> {
+    Page<EquipmentMaintain> findByPage(long pageNum, long pageSize,
+                                       String maintainId,String equipmentId,
+                                       String maintainType,String maintainPerson);
+
+    /**
+     * 新增设备维护记录
+     * @param entity
+     * @return
+     */
+    boolean saveWithCheck(EquipmentMaintain entity);
+
+    /**
+     * 批量新增设备维护记录
+     * @param entityList
+     * @return
+     */
+    boolean saveBatchWithCheck(List<EquipmentMaintain> entityList);
+
+    /**
+     * 修改设备维护记录
+     * @param entity
+     * @return
+     */
+    boolean updateWithCheck(EquipmentMaintain entity);
+}

+ 34 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/EquipmentStatusService.java

@@ -0,0 +1,34 @@
+package com.zksy.base.service;
+
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.zksy.base.domain.EquipmentStatus;
+import org.springframework.stereotype.Service;
+
+import java.util.List;
+
+@Service
+public interface EquipmentStatusService extends IService<EquipmentStatus> {
+
+    Page<EquipmentStatus> findByPage(long pageNum, long pageSize, String statusId,String equipmentId,Integer currentStatus,Integer alarmStatus,Integer onlineStatus,Long userId);
+    /**
+     * 批量新增仪器状态
+     * @param entityList
+     * @return
+     */
+    boolean saveBatchWithCheck(List<EquipmentStatus> entityList);
+
+    /**
+     * 新增仪器状态
+     * @param entity
+     * @return
+     */
+    boolean saveWithCheck(EquipmentStatus entity);
+
+    /**
+     * 修改仪器状态
+     * @param entity
+     * @return
+     */
+    boolean updateWithCheck(EquipmentStatus entity);
+}

+ 49 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/EquipmentTypeService.java

@@ -0,0 +1,49 @@
+package com.zksy.base.service;
+
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.zksy.base.domain.EquipmentType;
+import org.springframework.stereotype.Service;
+
+import java.util.List;
+
+@Service
+public interface EquipmentTypeService extends IService<EquipmentType> {
+
+    Page<EquipmentType> findByPage(long pageNum, long pageSize, String typeId,String typeName,String parentTypeId);
+
+    /**
+     * 新增设备类别
+     * @param entity
+     * @return
+     */
+    boolean saveWithCheck(EquipmentType entity);
+
+    /**
+     * 批量新增设备类别
+     * @param entityList
+     * @return
+     */
+    boolean saveBatchWithCheck(List<EquipmentType> entityList);
+
+    /**
+     * 设备类别修改
+     * @param entity
+     * @return
+     */
+    boolean updateWithCheck(EquipmentType entity);
+
+    /**
+     * 设备类别删除
+     * @param id
+     * @return
+     */
+    boolean removeWithCheck(String id);
+
+    /**
+     * 设备类别批量删除
+     * @param ids
+     * @return
+     */
+    boolean removeBatchWithCheck(List<String> ids);
+}

+ 224 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/impl/EquipmentBaseServiceImpl.java

@@ -0,0 +1,224 @@
+package com.zksy.base.service.impl;
+
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.zksy.base.domain.EquipmentBase;
+import com.zksy.base.domain.EquipmentMaintain;
+import com.zksy.base.domain.EquipmentStatus;
+import com.zksy.base.domain.EquipmentType;
+import com.zksy.base.mapper.EquipmentBaseMapper;
+import com.zksy.base.mapper.EquipmentMaintainMapper;
+import com.zksy.base.mapper.EquipmentStatusMapper;
+import com.zksy.base.mapper.EquipmentTypeMapper;
+import com.zksy.base.service.EquipmentBaseService;
+import com.zksy.common.exception.ServiceException;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+import java.util.stream.Collectors;
+
+@Slf4j
+@Service
+public class EquipmentBaseServiceImpl extends ServiceImpl<EquipmentBaseMapper, EquipmentBase>
+        implements EquipmentBaseService {
+
+    @Autowired
+    private EquipmentTypeMapper equipmentTypeMapper;
+
+    @Autowired
+    private EquipmentMaintainMapper equipmentMaintainMapper;
+
+    @Autowired
+    private EquipmentStatusMapper equipmentStatusMapper;
+
+//    @Autowired
+//    private EquipmentBaseMapper equipmentBaseMapper;
+
+    @Override
+    public Page<EquipmentBase> findByPage(long pageNum, long pageSize,
+                                          String equipmentCode,String equipmentName,
+                                          String equipmentModel,String manufacturer) {
+        Page<EquipmentBase> page = new Page<>(pageNum, pageSize);
+        LambdaQueryWrapper<EquipmentBase> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(EquipmentBase::getEquipmentCode,equipmentCode)
+                .eq(EquipmentBase::getEquipmentName,equipmentName)
+                .eq(EquipmentBase::getEquipmentModel,equipmentModel)
+                .eq(EquipmentBase::getManufacturer,manufacturer);
+        return this.page(page,queryWrapper);
+    }
+
+    /**
+     * 新增仪器信息
+     * @param entity
+     * @return
+     */
+    @Override
+    public boolean saveWithCheck(EquipmentBase entity) {
+        String equipmentTypeId = entity.getEquipmentTypeId();
+        EquipmentType equipmentType = equipmentTypeMapper.selectById(equipmentTypeId);
+        if(equipmentType==null){
+            throw new ServiceException("设备类型不存在,请检查equipment_type_id:");
+        }
+        //校验设备编码是否已存在
+        LambdaQueryWrapper<EquipmentBase> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(EquipmentBase::getEquipmentCode, entity.getEquipmentCode());
+        long count = this.count(queryWrapper);
+        if (count > 0) {
+            throw new ServiceException("设备编码已存在,请更换:" + entity.getEquipmentCode());
+        }
+        return this.save(entity);
+    }
+
+    /**
+     * 批量新增
+     * @param entityList
+     * @return
+     */
+    @Override
+    public boolean saveBatchWithCheck(List<EquipmentBase> entityList) {
+
+        //是否有重复编码
+        Set<String> codeSet = new HashSet<>();
+        for (EquipmentBase entity : entityList) {
+            String code = entity.getEquipmentCode();
+            if (codeSet.contains(code)) {
+                throw new ServiceException("列表中存在重复编码:" + code);
+            }
+            codeSet.add(code);
+        }
+
+        //校验
+        for (EquipmentBase entity : entityList) {
+            //校验设备类型是否存在
+            if (equipmentTypeMapper.selectById(entity.getEquipmentTypeId()) == null) {
+                throw new ServiceException("设备类型不存在:" + entity.getEquipmentTypeId());
+            }
+            //校验设备编码是否已存在
+            LambdaQueryWrapper<EquipmentBase> wrapper = new LambdaQueryWrapper<>();
+            wrapper.eq(EquipmentBase::getEquipmentCode, entity.getEquipmentCode());
+            if (this.count(wrapper) > 0) {
+                throw new ServiceException("设备编码已存在:" + entity.getEquipmentCode());
+            }
+        }
+        //保存
+        return this.saveBatch(entityList);
+    }
+
+    /**
+     * 修改仪器信息
+     * @param entity
+     * @return
+     */
+    @Override
+    @Transactional
+    public boolean updateWithCheck(EquipmentBase entity) {
+        //设备是否存在
+        String equipmentId = entity.getEquipmentId();
+        if (this.getById(equipmentId) == null) {
+            throw new ServiceException("设备不存在,无法修改:" + equipmentId);
+        }
+
+        //修改设备类型ID,需要校验新类型是否存在
+        String newTypeId = entity.getEquipmentTypeId();
+        if (newTypeId != null && equipmentTypeMapper.selectById(newTypeId) == null) {
+            throw new ServiceException("设备类型不存在:" + newTypeId);
+        }
+
+        //修改设备编码,需要校验新编码是否已被使用
+        String newCode = entity.getEquipmentCode();
+        if (newCode != null) {
+            LambdaQueryWrapper<EquipmentBase> wrapper = new LambdaQueryWrapper<>();
+            wrapper.eq(EquipmentBase::getEquipmentCode, newCode)
+                    .ne(EquipmentBase::getEquipmentId, equipmentId); // 排除自身
+            if (this.count(wrapper) > 0) {
+                throw new ServiceException("设备编码已被使用:" + newCode);
+            }
+        }
+        //修改
+        return this.updateById(entity);
+    }
+
+    /**
+     * 删除设备基础信息
+     * @param equipmentId
+     * @return
+     */
+    @Override
+    @Transactional
+    public boolean removeWithCheck(String equipmentId) {
+        //校验设备是否存在
+        EquipmentBase equipment = this.getById(equipmentId);
+        if (equipment == null) {
+            throw new ServiceException("设备不存在:" + equipmentId);
+        }
+
+        //删除关联的维护记录
+        LambdaQueryWrapper<EquipmentMaintain> maintainWrapper = new LambdaQueryWrapper<>();
+        maintainWrapper.eq(EquipmentMaintain::getEquipmentId, equipmentId);
+        equipmentMaintainMapper.delete(maintainWrapper);
+        log.info("已删除设备[{}]的维护记录", equipmentId);
+
+        //删除关联的状态记录
+        LambdaQueryWrapper<EquipmentStatus> statusWrapper = new LambdaQueryWrapper<>();
+        statusWrapper.eq(EquipmentStatus::getEquipmentId, equipmentId);
+        equipmentStatusMapper.delete(statusWrapper);
+        log.info("已删除设备[{}]的状态记录", equipmentId);
+
+        //删除设备
+        boolean deleted = this.baseMapper.deleteById(equipmentId) > 0;
+        return deleted;
+    }
+
+    /**
+     * 设备基础信息批量删除
+     * @param equipmentIds
+     * @return
+     */
+    @Override
+    @Transactional
+    public boolean removeBatchWithCheck(List<String> equipmentIds) {
+        if (CollectionUtils.isEmpty(equipmentIds)) {
+            throw new ServiceException("批量删除失败:设备ID列表不能为空");
+        }
+
+        //校验设备是否存在
+        List<EquipmentBase> existEquipments = this.listByIds(equipmentIds);
+        if (existEquipments.isEmpty()) {
+            throw new ServiceException("批量删除失败:所有设备ID均不存在");
+        }
+        // 提取存在的设备ID
+        List<String> existIds = existEquipments.stream()
+                .map(EquipmentBase::getEquipmentId)
+                .collect(Collectors.toList());
+        //无效ID
+        List<String> invalidIds = equipmentIds.stream()
+                .filter(id -> !existIds.contains(id))
+                .collect(Collectors.toList());
+        if (!invalidIds.isEmpty()) {
+            log.warn("批量删除中存在无效设备ID:{}", invalidIds);
+        }
+
+        //批量删除关联的维护记录
+        LambdaQueryWrapper<EquipmentMaintain> maintainWrapper = new LambdaQueryWrapper<>();
+        maintainWrapper.in(EquipmentMaintain::getEquipmentId, existIds);
+        equipmentMaintainMapper.delete(maintainWrapper);
+        log.info("已批量删除{}条设备的维护记录", existIds.size());
+
+        //批量删除关联的状态记录
+        LambdaQueryWrapper<EquipmentStatus> statusWrapper = new LambdaQueryWrapper<>();
+        statusWrapper.in(EquipmentStatus::getEquipmentId, existIds);
+        equipmentStatusMapper.delete(statusWrapper);
+        log.info("已批量删除{}条设备的状态记录", existIds.size());
+        //删除
+        return this.removeByIds(existIds);
+    }
+
+}

+ 134 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/impl/EquipmentMaintainServiceImpl.java

@@ -0,0 +1,134 @@
+package com.zksy.base.service.impl;
+
+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.zksy.base.domain.EquipmentBase;
+import com.zksy.base.domain.EquipmentMaintain;
+import com.zksy.base.mapper.EquipmentBaseMapper;
+import com.zksy.base.mapper.EquipmentMaintainMapper;
+import com.zksy.base.service.EquipmentMaintainService;
+import com.zksy.common.exception.ServiceException;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.util.List;
+import java.util.Set;
+import java.util.stream.Collectors;
+
+@Service
+public class EquipmentMaintainServiceImpl extends ServiceImpl<EquipmentMaintainMapper, EquipmentMaintain>
+        implements EquipmentMaintainService {
+
+    @Autowired
+    private EquipmentBaseMapper equipmentBaseMapper;
+
+    @Override
+    public Page<EquipmentMaintain> findByPage(long pageNum, long pageSize,
+                                              String maintainId,String equipmentId,
+                                              String maintainType,String maintainPerson) {
+        Page<EquipmentMaintain> page = new Page<>(pageNum, pageSize);
+        LambdaQueryWrapper<EquipmentMaintain> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(EquipmentMaintain::getMaintainId,maintainId)
+                    .eq(EquipmentMaintain::getEquipmentId,equipmentId)
+                    .eq(EquipmentMaintain::getMaintainType,maintainType)
+                    .eq(EquipmentMaintain::getMaintainPerson,maintainPerson);
+        return this.page(page,queryWrapper);
+    }
+
+    /**
+     * 新增设备维护记录
+     * @param entity
+     * @return
+     */
+    @Override
+    public boolean saveWithCheck(EquipmentMaintain entity) {
+        //校验关联的设备是否存在
+        String equipmentId = entity.getEquipmentId();
+        if (equipmentBaseMapper.selectById(equipmentId) == null) {
+            throw new ServiceException("关联的设备不存在:" + equipmentId);
+        }
+        //新增
+        return this.save(entity);
+    }
+
+    /**
+     * 批量新增设备维护记录
+     * @param entityList
+     * @return
+     */
+    @Override
+    @Transactional
+    public boolean saveBatchWithCheck(List<EquipmentMaintain> entityList) {
+        //批量校验设备ID是否存在
+        Set<String> equipmentIds = entityList.stream()
+                .map(EquipmentMaintain::getEquipmentId)
+                .collect(Collectors.toSet());
+        List<String> existEquipmentIds = equipmentBaseMapper.selectBatchIds(equipmentIds).stream()
+                .map(EquipmentBase::getEquipmentId)
+                .collect(Collectors.toList());
+        Set<String> invalidEquipmentIds = equipmentIds.stream()
+                .filter(id -> !existEquipmentIds.contains(id))
+                .collect(Collectors.toSet());
+
+        if (!invalidEquipmentIds.isEmpty()) {
+            throw new ServiceException("存在无效的设备ID:" + invalidEquipmentIds);
+        }
+
+        //校验
+        for (EquipmentMaintain entity : entityList) {
+            //校验关联的设备是否存在
+            String equipmentId = entity.getEquipmentId();
+            if (equipmentBaseMapper.selectById(equipmentId) == null) {
+                throw new ServiceException("关联的设备不存在:" + equipmentId + "(维护记录ID:" + entity.getMaintainId() + ")");
+            }
+
+            //校验核心必填字段
+//            if (entity.getMaintainPersonPhone() != null) {
+//                String phoneStr = String.valueOf(entity.getMaintainPersonPhone());
+//                if (phoneStr.length() != 11) {
+//                    throw new ServiceException("维护人手机号格式错误(需11位):" + phoneStr + "(维护记录ID:" + entity.getMaintainId() + ")");
+//                }
+//            }
+        }
+
+        //批量新增
+        return this.saveBatch(entityList);
+    }
+
+    /**
+     * 修改设备维护记录
+     * @param entity
+     * @return
+     */
+    @Override
+    @Transactional
+    public boolean updateWithCheck(EquipmentMaintain entity) {
+        //是否存在
+        String maintainId = entity.getMaintainId();
+        EquipmentMaintain oldRecord = this.getById(maintainId);
+        if (oldRecord == null) {
+            throw new ServiceException("维护记录不存在:" + maintainId);
+        }
+
+        //修改设备ID,需校验新设备是否存在
+        String newEquipmentId = entity.getEquipmentId();
+        if (newEquipmentId != null && !newEquipmentId.equals(oldRecord.getEquipmentId())) {
+            if (equipmentBaseMapper.selectById(newEquipmentId) == null) {
+                throw new ServiceException("新关联的设备不存在:" + newEquipmentId);
+            }
+        }
+
+//        //校验核心字段格式(可选)
+//        if (entity.getMaintainPersonPhone() != null) {
+//            String phoneStr = String.valueOf(entity.getMaintainPersonPhone());
+//            if (phoneStr.length() != 11) {
+//                throw new ServiceException("维护人手机号格式错误(需11位):" + phoneStr);
+//            }
+//        }
+
+        //更新
+        return this.updateById(entity);
+    }
+}

+ 192 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/impl/EquipmentStatusServiceImpl.java

@@ -0,0 +1,192 @@
+package com.zksy.base.service.impl;
+
+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.zksy.base.domain.EquipmentBase;
+import com.zksy.base.domain.EquipmentStatus;
+import com.zksy.base.mapper.EquipmentBaseMapper;
+import com.zksy.base.mapper.EquipmentStatusMapper;
+import com.zksy.base.service.EquipmentStatusService;
+import com.zksy.common.core.domain.entity.SysUser;
+import com.zksy.common.exception.ServiceException;
+import com.zksy.system.service.ISysUserService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+import java.util.stream.Collectors;
+
+@Service
+public class EquipmentStatusServiceImpl extends ServiceImpl<EquipmentStatusMapper, EquipmentStatus>
+        implements EquipmentStatusService {
+
+    @Autowired
+    private ISysUserService sysUserService;
+
+    @Autowired
+    private EquipmentBaseMapper equipmentBaseMapper;
+
+    @Override
+    public Page<EquipmentStatus> findByPage(long pageNum, long pageSize,
+                                            String statusId,String equipmentId,
+                                            Integer currentStatus,Integer alarmStatus,
+                                            Integer onlineStatus,Long userId) {
+        Page<EquipmentStatus> page = new Page<>(pageNum, pageSize);
+        LambdaQueryWrapper<EquipmentStatus> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(EquipmentStatus::getStatusId,statusId)
+                    .eq(EquipmentStatus::getCurrentStatus,currentStatus)
+                    .eq(EquipmentStatus::getAlarmStatus,alarmStatus)
+                    .eq(EquipmentStatus::getOnlineStatus,onlineStatus)
+                    .eq(EquipmentStatus::getUserId,userId);
+        return this.page(page,queryWrapper);
+    }
+
+    /**
+     * 新增仪器状态
+     * @param entity
+     * @return
+     */
+    @Override
+    public boolean saveWithCheck(EquipmentStatus entity) {
+        //校验关联的设备是否存在
+        String equipmentId = entity.getEquipmentId();
+        if (equipmentBaseMapper.selectById(equipmentId) == null) {
+            throw new ServiceException("关联的设备不存在:" + equipmentId);
+        }
+
+        //校验设备是否已存在状态记录
+        LambdaQueryWrapper<EquipmentStatus> wrapper = new LambdaQueryWrapper<>();
+        wrapper.eq(EquipmentStatus::getEquipmentId, equipmentId);
+        if (this.count(wrapper) > 0) {
+            throw new ServiceException("该设备已存在状态记录,不可重复新增:" + equipmentId);
+        }
+
+        //校验当前状态值是否合法(1-在用,2-闲置,3-维修,4-报废,5-待入库)
+        Integer currentStatus = entity.getCurrentStatus();
+        if (currentStatus == null || currentStatus < 1 || currentStatus > 5) {
+            throw new ServiceException("设备状态值无效,必须为1-5之间的整数:" + currentStatus);
+        }
+
+        //校验负责人ID
+        Long userId = entity.getUserId();
+        if (userId != null) {
+            SysUser user = sysUserService.selectUserById(userId);
+            if (user == null || "2".equals(user.getDelFlag())) { // 排除已删除的用户
+                throw new ServiceException("负责人ID不存在或已删除:" + userId);
+            }
+        }
+        //新增
+        return this.save(entity);
+    }
+
+    /**
+     * 批量新增仪器状态
+     * @param entityList
+     * @return
+     */
+    @Override
+    @Transactional
+    public boolean saveBatchWithCheck(List<EquipmentStatus> entityList) {
+        //批量校验id
+        List<String> equipmentIds = entityList.stream()
+                .map(EquipmentStatus::getEquipmentId)
+                .collect(Collectors.toList());
+
+        Set<String> duplicateEqIds = new HashSet<>();
+        Set<String> tempEqIds = new HashSet<>();
+        for (String eqId : equipmentIds) {
+            if (tempEqIds.contains(eqId)) {
+                duplicateEqIds.add(eqId);
+            } else {
+                tempEqIds.add(eqId);
+            }
+        }
+        if (!duplicateEqIds.isEmpty()) {
+            throw new ServiceException("批量列表中存在重复设备ID:" + duplicateEqIds);
+        }
+
+        // 校验设备是否存在,外键
+        List<String> existEqIds = equipmentBaseMapper.selectBatchIds(equipmentIds).stream()
+                .map(EquipmentBase::getEquipmentId)
+                .collect(Collectors.toList());
+        Set<String> invalidEqIds = equipmentIds.stream()
+                .filter(id -> !existEqIds.contains(id))
+                .collect(Collectors.toSet());
+        if (!invalidEqIds.isEmpty()) {
+            throw new ServiceException("存在无效的设备ID:" + invalidEqIds);
+        }
+
+        // 校验这些设备是否已存在状态记录
+        LambdaQueryWrapper<EquipmentStatus> wrapper = new LambdaQueryWrapper<>();
+        wrapper.in(EquipmentStatus::getEquipmentId, equipmentIds);
+        List<String> alreadyExistEqIds = this.list(wrapper).stream()
+                .map(EquipmentStatus::getEquipmentId)
+                .collect(Collectors.toList());
+        if (!alreadyExistEqIds.isEmpty()) {
+            throw new ServiceException("以下设备已存在状态记录,不能重复新增:" + alreadyExistEqIds);
+        }
+
+        //校验
+        for (EquipmentStatus entity : entityList) {
+            //校验状态值范围是否合法
+            Integer status = entity.getCurrentStatus();
+            if (status == null || status < 1 || status > 5) {
+                throw new ServiceException("设备状态值无效(必须为1-5):" + status + "(状态记录ID:" + entity.getStatusId() + ")");
+            }
+
+            //校验负责人ID
+            Long userId = entity.getUserId();
+            if (userId != null) {
+                SysUser user = sysUserService.selectUserById(userId);
+                if (user == null || "2".equals(user.getDelFlag())) { // 检查用户是否存在且未被删除
+                    throw new ServiceException("负责人不存在或已删除:" + userId + "(状态记录ID:" + entity.getStatusId() + ")");
+                }
+            }
+        }
+        //批量新增
+        return this.saveBatch(entityList);
+    }
+
+    /**
+     * 修改仪器状态
+     * @param entity
+     * @return
+     */
+    @Override
+    public boolean updateWithCheck(EquipmentStatus entity) {
+        //校验当前状态记录是否存在
+        String statusId = entity.getStatusId();
+        EquipmentStatus oldStatus = this.getById(statusId);
+        if (oldStatus == null) {
+            throw new ServiceException("设备状态记录不存在:" + statusId);
+        }
+
+        //校验设备ID是否被篡改
+        String newEqId = entity.getEquipmentId();
+        String oldEqId = oldStatus.getEquipmentId();
+        if (newEqId != null && !newEqId.equals(oldEqId)) {
+            throw new ServiceException("不允许修改设备ID(如需更换设备,请删除旧记录后重新新增)");
+        }
+
+        //校验状态值合法性
+        Integer status = entity.getCurrentStatus();
+        if (status != null && (status < 1 || status > 5)) {
+            throw new ServiceException("设备状态值无效(必须为1-5):" + status);
+        }
+
+        // 校验负责人ID
+        Long newUserId = entity.getUserId();
+        if (newUserId != null) {
+            SysUser user = sysUserService.selectUserById(newUserId);
+            if (user == null || "2".equals(user.getDelFlag())) {
+                throw new ServiceException("负责人不存在或已删除:" + newUserId);
+            }
+        }
+        //更新
+        return this.updateById(entity);
+    }
+}

+ 389 - 0
pipe-network-service/zksy-system/src/main/java/com/zksy/base/service/impl/EquipmentTypeServiceImpl.java

@@ -0,0 +1,389 @@
+package com.zksy.base.service.impl;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.zksy.base.domain.EquipmentBase;
+import com.zksy.base.domain.EquipmentType;
+import com.zksy.base.mapper.EquipmentBaseMapper;
+import com.zksy.base.mapper.EquipmentTypeMapper;
+import com.zksy.base.service.EquipmentBaseService;
+import com.zksy.base.service.EquipmentTypeService;
+import com.zksy.common.exception.ServiceException;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+
+import java.util.*;
+import java.util.stream.Collectors;
+
+//TODO 这里代码待检查
+@Slf4j
+@Service
+public class EquipmentTypeServiceImpl extends ServiceImpl<EquipmentTypeMapper, EquipmentType>
+        implements EquipmentTypeService {
+
+    @Autowired
+    private EquipmentBaseMapper equipmentBaseMapper;
+
+    @Autowired
+    private EquipmentBaseService equipmentBaseService;
+
+    @Override
+    public Page<EquipmentType> findByPage(long pageNum, long pageSize, String typeId,String typeName,String parentTypeId) {
+        Page<EquipmentType> page = new Page<>(pageNum, pageSize);
+        LambdaQueryWrapper<EquipmentType> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(EquipmentType::getTypeId,typeId)
+                    .eq(EquipmentType::getTypeName,typeName)
+                    .eq(EquipmentType::getParentTypeId,parentTypeId);
+        return this.page(page,queryWrapper);
+    }
+
+    /**
+     * 新增设备类别
+     * @param entity
+     * @return
+     */
+    @Override
+    public boolean saveWithCheck(EquipmentType entity) {
+        //校验父类别是否存在
+        String parentId = entity.getParentTypeId();
+        // 0表示无父类,无需校验
+        if (!"0".equals(parentId)) {
+            EquipmentType parent = this.getById(parentId);
+            if (parent == null) {
+                throw new ServiceException("父类别不存在:" + parentId);
+            }
+        }
+
+        //校验同一父类别下,类别名称是否重复
+        LambdaQueryWrapper<EquipmentType> wrapper = new LambdaQueryWrapper<>();
+        wrapper.eq(EquipmentType::getParentTypeId, parentId)
+                .eq(EquipmentType::getTypeName, entity.getTypeName());
+        if (this.count(wrapper) > 0) {
+            throw new ServiceException("同一父类别下已存在同名类别:" + entity.getTypeName());
+        }
+        //新增
+        return this.save(entity);
+    }
+
+    @Override
+    @Transactional
+    public boolean saveBatchWithCheck(List<EquipmentType> entityList) {
+
+        Set<String> parentIds = new HashSet<>(); // 所有父类别ID
+        Map<String, Set<String>> sameParentNames = new HashMap<>(); // 同一父类下的名称集合
+
+        for (EquipmentType entity : entityList) {
+            String parentId = entity.getParentTypeId() == null ? "0" : entity.getParentTypeId();
+            parentIds.add(parentId);
+
+            // 检查列表内同一父类下是否有重复名称
+            sameParentNames.computeIfAbsent(parentId, k -> new HashSet<>())
+                    .add(entity.getTypeName());
+        }
+
+        //批量校验父类别是否存在
+        List<String> existParentIds = this.listByIds(parentIds).stream()
+                .map(EquipmentType::getTypeId)
+                .collect(Collectors.toList());
+        // 过滤出不存在的父类别ID
+        Set<String> invalidParentIds = parentIds.stream()
+                .filter(id -> !"0".equals(id) && !existParentIds.contains(id))
+                .collect(Collectors.toSet());
+        if (!invalidParentIds.isEmpty()) {
+            throw new ServiceException("存在无效父类别ID:" + invalidParentIds);
+        }
+
+        //校验数据库中是否存在同名类别
+        for (Map.Entry<String, Set<String>> entry : sameParentNames.entrySet()) {
+            String parentId = entry.getKey();
+            Set<String> names = entry.getValue();
+
+            LambdaQueryWrapper<EquipmentType> wrapper = new LambdaQueryWrapper<>();
+            wrapper.eq(EquipmentType::getParentTypeId, parentId)
+                    .in(EquipmentType::getTypeName, names);
+
+            List<String> existNames = this.list(wrapper).stream()
+                    .map(EquipmentType::getTypeName)
+                    .collect(Collectors.toList());
+            if (!existNames.isEmpty()) {
+                throw new ServiceException("父类别[" + parentId + "]下已存在同名类别:" + existNames);
+            }
+        }
+
+        //批量保存
+        return this.saveBatch(entityList);
+    }
+
+    /**
+     * 设备类别修改
+     * @param entity
+     * @return
+     */
+    @Override
+    @Transactional
+    public boolean updateWithCheck(EquipmentType entity) {
+        //校验当前类别是否存在
+        String typeId = entity.getTypeId();
+        EquipmentType oldType = this.getById(typeId);
+        if (oldType == null) {
+            throw new ServiceException("设备类别不存在:" + typeId);
+        }
+
+        //处理父类别变更
+        String newParentId = entity.getParentTypeId() == null ? "0" : entity.getParentTypeId();
+        String oldParentId = oldType.getParentTypeId() == null ? "0" : oldType.getParentTypeId();
+
+        if (!newParentId.equals(oldParentId)) {
+            //新父类别必须存在
+            if (!"0".equals(newParentId)) {
+                EquipmentType newParent = this.getById(newParentId);
+                if (newParent == null) {
+                    throw new ServiceException("新父类别不存在:" + newParentId);
+                }
+                if (isChildOrSelf(newParentId, typeId)) {
+                    throw new ServiceException("不能将自身或子类别设为父类别:" + newParentId);
+                }
+            }
+        }
+
+        //处理类别名称修改
+        String newName = entity.getTypeName();
+        if (newName != null && !newName.equals(oldType.getTypeName())) {
+            // 同一父类别下不能有同名
+            LambdaQueryWrapper<EquipmentType> wrapper = new LambdaQueryWrapper<>();
+            wrapper.eq(EquipmentType::getParentTypeId, newParentId)
+                    .eq(EquipmentType::getTypeName, newName)
+                    .ne(EquipmentType::getTypeId, typeId); // 排除自身
+
+            if (this.count(wrapper) > 0) {
+                throw new ServiceException("父类别[" + newParentId + "]下已存在同名类别:" + newName);
+            }
+        }
+
+        //更新
+        return this.updateById(entity);
+    }
+
+    /**
+     * 设备类别删除
+     * @param typeId
+     * @return
+     */
+    @Transactional
+    public boolean removeWithCheck1(String typeId) {
+        // 校验类别是否存在
+        EquipmentType type = this.getById(typeId);
+        if (type == null) {
+            throw new ServiceException("设备类别不存在:" + typeId);
+        }
+
+        //校验是否有子设备关联
+        LambdaQueryWrapper<EquipmentBase> eqWrapper = new LambdaQueryWrapper<>();
+        eqWrapper.eq(EquipmentBase::getEquipmentTypeId, typeId);
+        //TODO 待完善
+        long relatedEqCount = equipmentBaseMapper.selectCount(eqWrapper);
+        if (relatedEqCount > 0) {
+            throw new ServiceException("该类别下存在" + relatedEqCount + "台设备,无法删除");
+        }
+
+        //校验是否有子类别依赖
+        LambdaQueryWrapper<EquipmentType> childWrapper = new LambdaQueryWrapper<>();
+        childWrapper.eq(EquipmentType::getParentTypeId, typeId);
+        long childTypeCount = this.count(childWrapper);
+        if (childTypeCount > 0) {
+            throw new ServiceException("该类别下存在" + childTypeCount + "个子类别,无法删除");
+        }
+
+        // 4. 执行删除
+//        boolean deleted = this.removeById(typeId);
+//        if (!deleted) {
+//            throw new ServiceException("设备类别删除失败:" + typeId);
+//        }
+        return this.removeById(typeId);
+    }
+
+    /**
+     * 设备类别批量删除
+     * @param typeIds
+     * @return
+     */
+
+    @Transactional
+    //TODO 这部分逻辑待优化,考虑删还是不删除,的概率是要删的
+    public boolean removeBatchWithCheck1(List<String> typeIds) {
+        // 1. 基础校验:ID列表不能为空
+        if (CollectionUtils.isEmpty(typeIds)) {
+            throw new ServiceException("批量删除失败:类别ID列表不能为空");
+        }
+
+        // 2. 校验类别是否存在(过滤无效ID)
+        List<EquipmentType> existTypes = this.listByIds(typeIds);
+        if (existTypes.isEmpty()) {
+            throw new ServiceException("批量删除失败:所有类别ID均不存在");
+        }
+        List<String> existIds = existTypes.stream()
+                .map(EquipmentType::getTypeId)
+                .collect(Collectors.toList());
+        // 记录无效ID(仅警告,不阻断)
+        List<String> invalidIds = typeIds.stream()
+                .filter(id -> !existIds.contains(id))
+                .collect(Collectors.toList());
+        if (!invalidIds.isEmpty()) {
+            log.warn("批量删除中存在无效类别ID:{}", invalidIds);
+        }
+
+        // 3. 校验是否有关联设备(批量检查)
+        LambdaQueryWrapper<EquipmentBase> eqWrapper = new LambdaQueryWrapper<>();
+        eqWrapper.in(EquipmentBase::getEquipmentTypeId, existIds);
+        //TODO 待完善,不确定方法用对没
+        List<String> relatedTypeIds = equipmentBaseMapper.selectList(eqWrapper).stream()
+                .map(EquipmentBase::getEquipmentTypeId)
+                .distinct() // 去重,获取有设备关联的类别ID
+                .collect(Collectors.toList());
+        if (!relatedTypeIds.isEmpty()) {
+            throw new ServiceException("以下类别存在关联设备,无法删除:" + relatedTypeIds);
+        }
+
+        // 4. 校验是否有子类别依赖(批量检查)
+        LambdaQueryWrapper<EquipmentType> childWrapper = new LambdaQueryWrapper<>();
+        childWrapper.in(EquipmentType::getParentTypeId, existIds);
+        List<String> hasChildTypeIds = this.list(childWrapper).stream()
+                .map(EquipmentType::getParentTypeId)
+                .distinct() // 去重,获取有子类别依赖的类别ID
+                .collect(Collectors.toList());
+        if (!hasChildTypeIds.isEmpty()) {
+            throw new ServiceException("以下类别存在子类别,无法删除:" + hasChildTypeIds);
+        }
+
+        // 5. 执行批量删除
+//        boolean deleted = this.removeByIds(existIds);
+//        if (!deleted) {
+//            throw new ServiceException("设备类别批量删除失败");
+//        }
+//        log.info("成功批量删除{}个设备类别", existIds.size());
+        return this.removeByIds(existIds);
+    }
+
+    /**
+     * 设备类别删除(强制删除,先删关联数据)
+     */
+    @Override
+    @Transactional
+    public boolean removeWithCheck(String typeId) {
+        // 校验类别是否存在
+        EquipmentType type = this.getById(typeId);
+        if (type == null) {
+            throw new ServiceException("设备类别不存在:" + typeId);
+        }
+
+        // 先删除关联的设备
+        LambdaQueryWrapper<EquipmentBase> eqWrapper = new LambdaQueryWrapper<>();
+        eqWrapper.eq(EquipmentBase::getEquipmentTypeId, typeId);
+        //TODO 待完善,不确定方法用对没
+        List<String> relatedEqIds = equipmentBaseMapper.selectList(eqWrapper).stream()
+                .map(EquipmentBase::getEquipmentId)
+                .collect(Collectors.toList());
+        if (!relatedEqIds.isEmpty()) {
+            equipmentBaseService.removeBatchWithCheck(relatedEqIds);
+            log.info("已级联删除类别[{}]关联的{}台设备", typeId, relatedEqIds.size());
+        }
+
+        // 先删除子类别
+        LambdaQueryWrapper<EquipmentType> childWrapper = new LambdaQueryWrapper<>();
+        childWrapper.eq(EquipmentType::getParentTypeId, typeId);
+        List<String> childTypeIds = this.list(childWrapper).stream()
+                .map(EquipmentType::getTypeId)
+                .collect(Collectors.toList());
+        if (!childTypeIds.isEmpty()) {
+            this.removeBatchWithCheck(childTypeIds); // 调用批量删除方法处理子类别
+            log.info("已删除类别[{}]的{}个子类别", typeId, childTypeIds.size());
+        }
+        //删除
+        return this.removeById(typeId);
+    }
+
+    /**
+     * 设备类别批量删除(强制删除,先删关联数据)
+     */
+    @Override
+    @Transactional
+    public boolean removeBatchWithCheck(List<String> typeIds) {
+        if (CollectionUtils.isEmpty(typeIds)) {
+            throw new ServiceException("批量删除失败:类别ID列表不能为空");
+        }
+
+        //校验类别是否存在
+        List<EquipmentType> existTypes = this.listByIds(typeIds);
+        if (existTypes.isEmpty()) {
+            throw new ServiceException("批量删除失败:所有类别ID均不存在");
+        }
+        List<String> existIds = existTypes.stream()
+                .map(EquipmentType::getTypeId)
+                .collect(Collectors.toList());
+        List<String> invalidIds = typeIds.stream()
+                .filter(id -> !existIds.contains(id))
+                .collect(Collectors.toList());
+        if (!invalidIds.isEmpty()) {
+            log.warn("批量删除中存在无效类别ID:{}", invalidIds);
+        }
+
+        //先批量删除所有关联的设备
+        LambdaQueryWrapper<EquipmentBase> eqWrapper = new LambdaQueryWrapper<>();
+        eqWrapper.in(EquipmentBase::getEquipmentTypeId, existIds);
+        //TODO 待完善,不确定方法用对没
+        List<String> relatedEqIds = equipmentBaseMapper.selectList(eqWrapper).stream()
+                .map(EquipmentBase::getEquipmentId)
+                .collect(Collectors.toList());
+        if (!relatedEqIds.isEmpty()) {
+            equipmentBaseService.removeBatchWithCheck(relatedEqIds);
+            log.info("已批量级联删除{}台关联设备", relatedEqIds.size());
+        }
+
+        //先批量删除所有子类别
+        List<String> allChildTypeIds = new ArrayList<>();
+        collectAllChildTypes(existIds, allChildTypeIds); // 递归收集所有子类别ID
+        if (!allChildTypeIds.isEmpty()) {
+            this.removeBatchWithCheck(allChildTypeIds); // 批量删除所有子类别
+            log.info("已批量删除{}个子类别", allChildTypeIds.size());
+        }
+
+        return this.removeByIds(existIds);
+    }
+
+    /**
+     * 递归收集所有层级的子类别ID
+     */
+    private void collectAllChildTypes(List<String> parentTypeIds, List<String> allChildTypeIds) {
+        LambdaQueryWrapper<EquipmentType> wrapper = new LambdaQueryWrapper<>();
+        wrapper.in(EquipmentType::getParentTypeId, parentTypeIds);
+        List<String> childIds = this.list(wrapper).stream()
+                .map(EquipmentType::getTypeId)
+                .collect(Collectors.toList());
+        if (!childIds.isEmpty()) {
+            allChildTypeIds.addAll(childIds);
+            collectAllChildTypes(childIds, allChildTypeIds); // 递归收集下一级子类别
+        }
+    }
+
+    //检查targetId是否是currentId的子类别或自身
+    private boolean isChildOrSelf(String targetId, String currentId) {
+        if (targetId.equals(currentId)) {
+            //自身不能作为父类别
+            return true;
+        }
+        // 查询targetId的所有子类别
+        LambdaQueryWrapper<EquipmentType> wrapper = new LambdaQueryWrapper<>();
+        wrapper.eq(EquipmentType::getParentTypeId, targetId);
+        List<EquipmentType> children = this.list(wrapper);
+        for (EquipmentType child : children) {
+            if (child.getTypeId().equals(currentId) || isChildOrSelf(child.getTypeId(), currentId)) {
+                return true;
+            }
+        }
+        return false;
+    }
+}