|
@@ -2,18 +2,25 @@ package com.zksy.drainage.service.impl;
|
|
|
|
|
|
|
|
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
|
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
|
|
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
|
|
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
|
|
|
|
|
+import com.baomidou.mybatisplus.core.toolkit.support.SFunction;
|
|
|
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
|
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
|
|
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
|
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
|
|
import com.zksy.common.exception.ServiceException;
|
|
import com.zksy.common.exception.ServiceException;
|
|
|
import com.zksy.drainage.domain.WaterloggingPoint;
|
|
import com.zksy.drainage.domain.WaterloggingPoint;
|
|
|
|
|
+import com.zksy.drainage.dto.WaterloggingPointPageInDTO;
|
|
|
import com.zksy.drainage.mapper.WaterloggingPointMapper;
|
|
import com.zksy.drainage.mapper.WaterloggingPointMapper;
|
|
|
-import com.zksy.drainage.service.DrainageEquipmentBindingService;
|
|
|
|
|
import com.zksy.drainage.service.WaterloggingPointService;
|
|
import com.zksy.drainage.service.WaterloggingPointService;
|
|
|
import lombok.extern.slf4j.Slf4j;
|
|
import lombok.extern.slf4j.Slf4j;
|
|
|
import org.springframework.stereotype.Service;
|
|
import org.springframework.stereotype.Service;
|
|
|
import org.springframework.transaction.annotation.Transactional;
|
|
import org.springframework.transaction.annotation.Transactional;
|
|
|
|
|
|
|
|
|
|
+import java.time.LocalDateTime;
|
|
|
|
|
+import java.util.ArrayList;
|
|
|
|
|
+import java.util.LinkedHashMap;
|
|
|
|
|
+import java.util.LinkedHashSet;
|
|
|
import java.util.List;
|
|
import java.util.List;
|
|
|
|
|
+import java.util.Map;
|
|
|
|
|
+import java.util.Set;
|
|
|
import java.util.stream.Collectors;
|
|
import java.util.stream.Collectors;
|
|
|
|
|
|
|
|
/**
|
|
/**
|
|
@@ -24,57 +31,144 @@ import java.util.stream.Collectors;
|
|
|
public class WaterloggingPointServiceImpl extends ServiceImpl<WaterloggingPointMapper, WaterloggingPoint>
|
|
public class WaterloggingPointServiceImpl extends ServiceImpl<WaterloggingPointMapper, WaterloggingPoint>
|
|
|
implements WaterloggingPointService {
|
|
implements WaterloggingPointService {
|
|
|
|
|
|
|
|
- @org.springframework.beans.factory.annotation.Autowired
|
|
|
|
|
- private DrainageEquipmentBindingService equipmentBindingService;
|
|
|
|
|
-
|
|
|
|
|
@org.springframework.beans.factory.annotation.Autowired
|
|
@org.springframework.beans.factory.annotation.Autowired
|
|
|
private com.zksy.drainage.mapper.DrainageBindingLockMapper bindingLock;
|
|
private com.zksy.drainage.mapper.DrainageBindingLockMapper bindingLock;
|
|
|
|
|
|
|
|
@Override
|
|
@Override
|
|
|
- public Page<WaterloggingPoint> findByPage(long pageNum, long pageSize, String name, String area) {
|
|
|
|
|
- Page<WaterloggingPoint> page = new Page<>(pageNum, pageSize);
|
|
|
|
|
|
|
+ public Page<WaterloggingPoint> findByPage(WaterloggingPointPageInDTO dto) {
|
|
|
|
|
+ WaterloggingPointPageInDTO query = dto == null ? new WaterloggingPointPageInDTO() : dto;
|
|
|
|
|
+ long pageNum = query.getPageNum() == null || query.getPageNum() < 1 ? 1 : query.getPageNum();
|
|
|
|
|
+ long pageSize = query.getPageSize() == null || query.getPageSize() < 1 ? 10 : query.getPageSize();
|
|
|
|
|
+ return this.page(new Page<>(pageNum, pageSize), buildWrapper(query));
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ @Override
|
|
|
|
|
+ public List<WaterloggingPoint> listForMap(WaterloggingPointPageInDTO dto) {
|
|
|
|
|
+ WaterloggingPointPageInDTO query = dto == null ? new WaterloggingPointPageInDTO() : dto;
|
|
|
|
|
+ LambdaQueryWrapper<WaterloggingPoint> wrapper = buildWrapper(query);
|
|
|
|
|
+ wrapper.isNotNull(WaterloggingPoint::getLongitude)
|
|
|
|
|
+ .isNotNull(WaterloggingPoint::getLatitude)
|
|
|
|
|
+ .orderByAsc(WaterloggingPoint::getPointCode);
|
|
|
|
|
+ return this.list(wrapper);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ @Override
|
|
|
|
|
+ public Map<String, List<String>> getFilterOptions() {
|
|
|
|
|
+ Map<String, List<String>> options = new LinkedHashMap<>();
|
|
|
|
|
+ options.put("district", distinctValues(WaterloggingPoint::getDistrict));
|
|
|
|
|
+ options.put("waterloggingLevel", distinctValues(WaterloggingPoint::getWaterloggingLevel));
|
|
|
|
|
+ options.put("riskLevel", distinctValues(WaterloggingPoint::getRiskLevel));
|
|
|
|
|
+ return options;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /**
|
|
|
|
|
+ * 分页与地图共用同一套筛选条件,避免口径漂移。
|
|
|
|
|
+ */
|
|
|
|
|
+ private LambdaQueryWrapper<WaterloggingPoint> buildWrapper(WaterloggingPointPageInDTO query) {
|
|
|
LambdaQueryWrapper<WaterloggingPoint> wrapper = new LambdaQueryWrapper<>();
|
|
LambdaQueryWrapper<WaterloggingPoint> wrapper = new LambdaQueryWrapper<>();
|
|
|
- if (name != null && !name.isEmpty()) {
|
|
|
|
|
- wrapper.like(WaterloggingPoint::getName, name);
|
|
|
|
|
- }
|
|
|
|
|
- if (area != null && !area.isEmpty()) {
|
|
|
|
|
- wrapper.like(WaterloggingPoint::getArea, area);
|
|
|
|
|
- }
|
|
|
|
|
|
|
+ wrapper.like(hasText(query.getPointCode()), WaterloggingPoint::getPointCode, query.getPointCode());
|
|
|
|
|
+ wrapper.like(hasText(query.getPointName()), WaterloggingPoint::getPointName, query.getPointName());
|
|
|
|
|
+ wrapper.like(hasText(query.getDistrict()), WaterloggingPoint::getDistrict, query.getDistrict());
|
|
|
|
|
+ wrapper.eq(query.getWaterloggingLevel() != null,
|
|
|
|
|
+ WaterloggingPoint::getWaterloggingLevel, query.getWaterloggingLevel());
|
|
|
|
|
+ wrapper.eq(hasText(query.getRiskLevel()), WaterloggingPoint::getRiskLevel, query.getRiskLevel());
|
|
|
wrapper.orderByDesc(WaterloggingPoint::getCreateTime);
|
|
wrapper.orderByDesc(WaterloggingPoint::getCreateTime);
|
|
|
- return this.page(page, wrapper);
|
|
|
|
|
|
|
+ return wrapper;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private boolean hasText(String value) {
|
|
|
|
|
+ return value != null && !value.trim().isEmpty();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private List<String> distinctValues(SFunction<WaterloggingPoint, ?> column) {
|
|
|
|
|
+ List<WaterloggingPoint> rows = this.list(new LambdaQueryWrapper<WaterloggingPoint>()
|
|
|
|
|
+ .select(column)
|
|
|
|
|
+ .isNotNull(column)
|
|
|
|
|
+ .groupBy(column));
|
|
|
|
|
+ List<String> values = new ArrayList<>(rows.size());
|
|
|
|
|
+ for (WaterloggingPoint row : rows) {
|
|
|
|
|
+ Object value = column.apply(row);
|
|
|
|
|
+ if (value != null && !String.valueOf(value).trim().isEmpty()) {
|
|
|
|
|
+ values.add(String.valueOf(value).trim());
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ return values.stream().distinct().sorted().collect(Collectors.toList());
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
@Override
|
|
|
@Transactional
|
|
@Transactional
|
|
|
public boolean saveWithCheck(WaterloggingPoint entity) {
|
|
public boolean saveWithCheck(WaterloggingPoint entity) {
|
|
|
bindingLock.lock();
|
|
bindingLock.lock();
|
|
|
- String equipmentIds = entity.getEquipmentId();
|
|
|
|
|
- entity.setEquipmentId("");
|
|
|
|
|
|
|
+ String cameraIds = entity.getCameraIds();
|
|
|
|
|
+ entity.setCameraIds(null);
|
|
|
|
|
+ entity.setCreateTime(LocalDateTime.now());
|
|
|
|
|
+ entity.setUpdateTime(LocalDateTime.now());
|
|
|
if (!this.save(entity)) return false;
|
|
if (!this.save(entity)) return false;
|
|
|
- if (equipmentIds != null && !equipmentIds.isBlank())
|
|
|
|
|
- equipmentBindingService.bindEquipment(DrainageEquipmentBindingService.TYPE_WATERLOGGING,
|
|
|
|
|
- entity.getId(), java.util.Arrays.asList(equipmentIds.split(",")));
|
|
|
|
|
- return true;
|
|
|
|
|
|
|
+ return applyCameras(entity.getPointId(), cameraIds);
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
@Override
|
|
|
@Transactional
|
|
@Transactional
|
|
|
public boolean updateWithCheck(WaterloggingPoint entity) {
|
|
public boolean updateWithCheck(WaterloggingPoint entity) {
|
|
|
bindingLock.lock();
|
|
bindingLock.lock();
|
|
|
- String id = entity.getId();
|
|
|
|
|
- if (this.getById(id) == null) {
|
|
|
|
|
- throw new ServiceException("易积水点不存在,无法修改:" + id);
|
|
|
|
|
|
|
+ String pointId = entity.getPointId();
|
|
|
|
|
+ if (this.getById(pointId) == null) {
|
|
|
|
|
+ throw new ServiceException("易积水点不存在,无法修改:" + pointId);
|
|
|
}
|
|
}
|
|
|
- String equipmentIds = entity.getEquipmentId();
|
|
|
|
|
- entity.setEquipmentId(null);
|
|
|
|
|
|
|
+ String cameraIds = entity.getCameraIds();
|
|
|
|
|
+ entity.setCameraIds(null);
|
|
|
|
|
+ entity.setUpdateTime(LocalDateTime.now());
|
|
|
if (!this.updateById(entity)) return false;
|
|
if (!this.updateById(entity)) return false;
|
|
|
- if (equipmentIds != null && !equipmentIds.isBlank())
|
|
|
|
|
- equipmentBindingService.bindEquipment(DrainageEquipmentBindingService.TYPE_WATERLOGGING,
|
|
|
|
|
- id, java.util.Arrays.asList(equipmentIds.split(",")));
|
|
|
|
|
- else if (equipmentIds != null)
|
|
|
|
|
- this.baseMapper.update(null, new com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper<WaterloggingPoint>()
|
|
|
|
|
- .eq(WaterloggingPoint::getId, id).set(WaterloggingPoint::getEquipmentId, ""));
|
|
|
|
|
- return true;
|
|
|
|
|
|
|
+ // cameraIds 传 null 表示本次不动关联;传空串表示解除全部关联
|
|
|
|
|
+ if (cameraIds == null) return true;
|
|
|
|
|
+ return applyCameras(pointId, cameraIds);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /**
|
|
|
|
|
+ * 整体替换某点位的摄像头关联,并校验摄像头是否已被其他点位占用。
|
|
|
|
|
+ */
|
|
|
|
|
+ private boolean applyCameras(String pointId, String cameraIds) {
|
|
|
|
|
+ List<String> normalized = parseIds(cameraIds);
|
|
|
|
|
+ checkCameraOccupation(pointId, normalized);
|
|
|
|
|
+ WaterloggingPoint patch = new WaterloggingPoint();
|
|
|
|
|
+ patch.setPointId(pointId);
|
|
|
|
|
+ patch.setCameraIds(String.join(",", normalized));
|
|
|
|
|
+ patch.setUpdateTime(LocalDateTime.now());
|
|
|
|
|
+ return this.updateById(patch);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ @Override
|
|
|
|
|
+ @Transactional
|
|
|
|
|
+ public boolean bindCameras(String pointId, List<String> cameraIds) {
|
|
|
|
|
+ bindingLock.lock();
|
|
|
|
|
+ if (this.getById(pointId) == null) {
|
|
|
|
|
+ throw new ServiceException("易积水点不存在:" + pointId);
|
|
|
|
|
+ }
|
|
|
|
|
+ List<String> normalized = normalizeIds(cameraIds);
|
|
|
|
|
+ checkCameraOccupation(pointId, normalized);
|
|
|
|
|
+ WaterloggingPoint patch = new WaterloggingPoint();
|
|
|
|
|
+ patch.setPointId(pointId);
|
|
|
|
|
+ patch.setCameraIds(String.join(",", normalized));
|
|
|
|
|
+ patch.setUpdateTime(LocalDateTime.now());
|
|
|
|
|
+ return this.updateById(patch);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /** 摄像头只能挂在一个易积水点上,避免摄像头不在现场却出现在两个点位。 */
|
|
|
|
|
+ private void checkCameraOccupation(String pointId, List<String> cameraIds) {
|
|
|
|
|
+ if (cameraIds.isEmpty()) return;
|
|
|
|
|
+ List<WaterloggingPoint> others = this.list(new LambdaQueryWrapper<WaterloggingPoint>()
|
|
|
|
|
+ .ne(WaterloggingPoint::getPointId, pointId)
|
|
|
|
|
+ .isNotNull(WaterloggingPoint::getCameraIds));
|
|
|
|
|
+ for (WaterloggingPoint other : others) {
|
|
|
|
|
+ Set<String> occupied = parseIds(other.getCameraIds()).stream()
|
|
|
|
|
+ .collect(Collectors.toCollection(LinkedHashSet::new));
|
|
|
|
|
+ for (String cameraId : cameraIds) {
|
|
|
|
|
+ if (occupied.contains(cameraId)) {
|
|
|
|
|
+ String name = hasText(other.getPointName()) ? other.getPointName() : other.getPointId();
|
|
|
|
|
+ throw new ServiceException("摄像头已被易积水点「" + name + "」关联,请先解除");
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
@Override
|
|
@@ -99,14 +193,23 @@ public class WaterloggingPointServiceImpl extends ServiceImpl<WaterloggingPointM
|
|
|
throw new ServiceException("批量删除失败:所有ID均不存在");
|
|
throw new ServiceException("批量删除失败:所有ID均不存在");
|
|
|
}
|
|
}
|
|
|
List<String> existIds = existing.stream()
|
|
List<String> existIds = existing.stream()
|
|
|
- .map(WaterloggingPoint::getId)
|
|
|
|
|
|
|
+ .map(WaterloggingPoint::getPointId)
|
|
|
.collect(Collectors.toList());
|
|
.collect(Collectors.toList());
|
|
|
return this.removeByIds(existIds);
|
|
return this.removeByIds(existIds);
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
- @Override
|
|
|
|
|
- public boolean bindEquipment(String id, List<String> equipmentIds) {
|
|
|
|
|
- return equipmentBindingService.bindEquipment(
|
|
|
|
|
- DrainageEquipmentBindingService.TYPE_WATERLOGGING, id, equipmentIds);
|
|
|
|
|
|
|
+ private List<String> parseIds(String value) {
|
|
|
|
|
+ if (value == null || value.trim().isEmpty()) return new ArrayList<>();
|
|
|
|
|
+ return normalizeIds(java.util.Arrays.asList(value.split(",")));
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ private List<String> normalizeIds(List<String> ids) {
|
|
|
|
|
+ if (ids == null) return new ArrayList<>();
|
|
|
|
|
+ return ids.stream()
|
|
|
|
|
+ .filter(java.util.Objects::nonNull)
|
|
|
|
|
+ .map(String::trim)
|
|
|
|
|
+ .filter(s -> !s.isEmpty())
|
|
|
|
|
+ .distinct()
|
|
|
|
|
+ .collect(Collectors.toList());
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|