package com.ard.work.service.control; import com.ard.common.exception.ControlException; import com.ard.common.utils.SecurityUtils; import com.ard.system.service.ISysUserService; import com.ard.work.component.websocket.handler.UavControlManager; import com.ard.work.domain.message.UavControlType; import org.springframework.stereotype.Service; import javax.annotation.Resource; import java.util.HashMap; import java.util.Map; import java.util.Set; import java.util.concurrent.ConcurrentHashMap; /** * UAV控制服务类,负责管理对飞行和载荷的控制请求、释放和权限管理 * 支持优先级抢占 */ @Service public class UavControlService { @Resource private UavControlManager uavControlManager; @Resource private ISysUserService sysUserService; /** * 当前飞行控制权限用户 */ private final ConcurrentHashMap uavFlyControlMap = new ConcurrentHashMap<>(); /** * 当前载荷控制权限用户 */ private final ConcurrentHashMap uavPayloadControlMap = new ConcurrentHashMap<>(); /** * 飞行控制请求:boxSn -> 多个请求者 */ private final ConcurrentHashMap> flyControlRequests = new ConcurrentHashMap<>(); /** * 载荷控制请求 */ private final ConcurrentHashMap> payloadControlRequests = new ConcurrentHashMap<>(); /** * 请求获取 UAV 控制权限 */ public boolean requestControl(String boxSn, String type) { UavControlType controlType = UavControlType.fromString(type); Long requester = SecurityUtils.getUserId(); return requestSingleControl(boxSn, controlType, requester); } /** * 处理单个控制类型的请求 */ /** * 处理单个控制类型的请求(支持多请求者) */ private boolean requestSingleControl(String boxSn, UavControlType controlType, Long requester) { ConcurrentHashMap controlMap = getControlMap(controlType); ConcurrentHashMap> requestMap = getRequestMap(controlType); Long controller = controlMap.get(boxSn); // 无人控制 → 直接获取 if (controller == null) { controlMap.put(boxSn, requester); uavControlManager.sendControlApproval(requester, boxSn, controlType.getType(), requester); return true; } // 已是控制者 if (controller.equals(requester)) { throw new ControlException("当前已拥有控制权"); } int requesterPriority = getUserPriority(requester); int controllerPriority = getUserPriority(controller); // 优先级高 → 直接接管 if (requesterPriority > controllerPriority) { controlMap.put(boxSn, requester); // 通知原控制者被抢占 uavControlManager.sendControlTakeover(controller, requester, boxSn, controlType.getType()); return true; } // ===== 以下是关键改动点 ===== // 优先级相同或更低 → 加入请求集合(不覆盖) Set requesters = requestMap.computeIfAbsent(boxSn, k -> ConcurrentHashMap.newKeySet()); requesters.add(requester); // 通知当前控制者:有新的请求者 uavControlManager.sendControlRequest(controller, boxSn, controlType.getType(), requester); return false; } /** * 处理 UAV 控制请求的响应 */ public boolean handleControlResponse(String boxSn, boolean approve, String type, Long requester) { UavControlType controlType = UavControlType.fromString(type); Long controller = SecurityUtils.getUserId(); return handleSingleControlResponse(boxSn, approve, controlType, controller, requester); } /** * 处理单个控制类型请求响应 */ private boolean handleSingleControlResponse(String boxSn, boolean approve, UavControlType controlType, Long controller, Long requester) { ConcurrentHashMap> requestMap = getRequestMap(controlType); Set requesters = requestMap.get(boxSn); if (requesters == null || !requesters.contains(requester)) { throw new ControlException("无控制请求"); } if (approve) { getControlMap(controlType).put(boxSn, requester); // 通知被批准者 uavControlManager.sendControlApproval(requester, boxSn, controlType.getType(), controller); // 🚨 其他请求者自动拒绝(强烈建议) for (Long other : requesters) { if (!other.equals(requester)) { uavControlManager.sendControlRejection(other, boxSn, controlType.getType(), controller); } } } else { uavControlManager.sendControlRejection(requester, boxSn, controlType.getType(), controller); } requesters.remove(requester); if (requesters.isEmpty()) { requestMap.remove(boxSn); } return true; } /** * 释放 UAV 控制权限 */ public boolean releaseControl(String boxSn, String type) { UavControlType controlType = UavControlType.fromString(type); Long controller = SecurityUtils.getUserId(); return releaseSingleControl(boxSn, controlType, controller); } /** * 释放单个控制类型权限 */ private boolean releaseSingleControl(String boxSn, UavControlType controlType, Long controller) { ConcurrentHashMap controlMap = getControlMap(controlType); if (!controller.equals(controlMap.get(boxSn))) { throw new ControlException("没有该设备的" + controlType.getType().toUpperCase() + "控制权"); } controlMap.remove(boxSn); uavControlManager.sendControlRelease(boxSn, controlType.getType(), controller); return true; } /** * 释放用户所有控制权限 */ public void releaseAllControls(Long userId) { uavFlyControlMap.entrySet().removeIf(entry -> entry.getValue().equals(userId)); uavPayloadControlMap.entrySet().removeIf(entry -> entry.getValue().equals(userId)); } /** * 获取当前某设备的控制用户 */ public Long getCurrentController(String boxSn, String type) { UavControlType controlType = UavControlType.fromString(type); return getControlMap(controlType).get(boxSn); } public Map getCurrentController(String boxSn) { Map map = new HashMap<>(); map.put("flyController", uavFlyControlMap.get(boxSn)); map.put("payloadController", uavPayloadControlMap.get(boxSn)); return map; } /** * 根据控制类型获取对应控制 Map */ private ConcurrentHashMap getControlMap(UavControlType controlType) { switch (controlType) { case FLY: return uavFlyControlMap; case PAYLOAD: return uavPayloadControlMap; default: throw new IllegalArgumentException("不支持的控制类型"); } } /** * 根据控制类型获取对应请求 Map */ private ConcurrentHashMap> getRequestMap(UavControlType controlType) { switch (controlType) { case FLY: return flyControlRequests; case PAYLOAD: return payloadControlRequests; default: throw new IllegalArgumentException("不支持的控制类型"); } } /** * 获取用户优先级 */ private int getUserPriority(Long userId) { return sysUserService.selectUserById(userId).getPriority(); } }