diff --git a/qaup-admin/src/main/resources/application-prod.yml b/qaup-admin/src/main/resources/application-prod.yml index d7f4883..109acb3 100644 --- a/qaup-admin/src/main/resources/application-prod.yml +++ b/qaup-admin/src/main/resources/application-prod.yml @@ -21,7 +21,7 @@ spring: # Redis配置(支持环境变量) data: redis: - host: ${REDIS_HOST:localhost} + host: ${REDIS_HOST:10.0.0.58} port: ${REDIS_PORT:6379} database: ${REDIS_DATABASE:0} password: ${REDIS_PASSWORD:} @@ -77,8 +77,8 @@ data: retry-attempts: ${VEHICLE_API_RETRY:3} vehicle-manager: - host: ${VEHICLE_MANAGER_HOST:} - port: ${VEHICLE_MANAGER_PORT:0} + host: ${VEHICLE_MANAGER_HOST:localhost} + port: ${VEHICLE_MANAGER_PORT:8020} reconnect-delay-millis: ${VEHICLE_MANAGER_RECONNECT_DELAY:3000} ws: at-manager: /ws/at_manager diff --git a/qaup-admin/src/main/resources/application.yml b/qaup-admin/src/main/resources/application.yml index 2dbe71d..f349577 100644 --- a/qaup-admin/src/main/resources/application.yml +++ b/qaup-admin/src/main/resources/application.yml @@ -40,7 +40,7 @@ spring: # 默认激活的profile(开发环境) profiles: - # active: dev,druid + #active: dev,druid active: prod,druid # 文件上传 diff --git a/qaup-collision/src/main/java/com/qaup/collision/controller/VehicleManagerApiController.java b/qaup-collision/src/main/java/com/qaup/collision/controller/VehicleManagerApiController.java index a2eb7ed..74fe1c5 100644 --- a/qaup-collision/src/main/java/com/qaup/collision/controller/VehicleManagerApiController.java +++ b/qaup-collision/src/main/java/com/qaup/collision/controller/VehicleManagerApiController.java @@ -38,6 +38,16 @@ public class VehicleManagerApiController { return AjaxResult.success(summary).put("timestamp", System.currentTimeMillis()); } + @GetMapping("/vehicles") + public AjaxResult getVehicleList( + @RequestParam(defaultValue = "1") int pageNum, + @RequestParam(defaultValue = "10") int pageSize, + @RequestParam(required = false) String status, + @RequestParam(defaultValue = "30000") long staleMillis) { + VehicleManagerQueryService.VehicleListResponse response = queryService.getVehicleList(pageNum, pageSize, status, staleMillis); + return AjaxResult.success(response).put("timestamp", System.currentTimeMillis()); + } + @GetMapping("/vehicles/{vehicleId}") public AjaxResult getVehicleSnapshot(@PathVariable String vehicleId) { Map snapshot = queryService.getVehicleSnapshot(vehicleId); @@ -122,8 +132,8 @@ public class VehicleManagerApiController { Double y = getDouble(node, "y"); waypoints.add(MissionContextDTO.WaypointDTO.builder() .waypointId(String.valueOf(index++)) - .longitude(x) - .latitude(y) + .longitude(y) + .latitude(x) .status("PENDING") .build()); } diff --git a/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/DataCollectorService.java b/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/DataCollectorService.java index 10aa162..be05df8 100644 --- a/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/DataCollectorService.java +++ b/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/DataCollectorService.java @@ -297,7 +297,7 @@ public class DataCollectorService { Double x = getDouble(dataNode, "x"); Double y = getDouble(dataNode, "y"); if (x != null && y != null) { - Point currentPosition = geometryFactory.createPoint(new org.locationtech.jts.geom.Coordinate(x, y)); + Point currentPosition = geometryFactory.createPoint(new org.locationtech.jts.geom.Coordinate(y, x)); MovingObject existing = activeMovingObjectsCache.get(vehicleId); UnmannedVehicle vehicle = existing instanceof UnmannedVehicle diff --git a/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/VehicleManagerQueryService.java b/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/VehicleManagerQueryService.java index b88314b..5031f69 100644 --- a/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/VehicleManagerQueryService.java +++ b/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/VehicleManagerQueryService.java @@ -6,9 +6,7 @@ import lombok.Data; import lombok.RequiredArgsConstructor; import org.springframework.stereotype.Service; -import java.util.HashMap; -import java.util.Map; -import java.util.Set; +import java.util.*; @Service @RequiredArgsConstructor @@ -187,4 +185,166 @@ public class VehicleManagerQueryService { } return value.asText(); } + + @Data + @Builder + public static class VehicleListItemDTO { + private String vehicleId; + private String vehicleType; + private String status; + private Map position; + private Double speed; + private Double batteryLevel; + private Long lastSeenAt; + private Boolean isEmergency; + private Boolean isFault; + private String currentTask; + } + + @Data + @Builder + public static class VehicleListResponse { + private int total; + private int pageNum; + private int pageSize; + private List rows; + private VehicleSummary summary; + } + + public VehicleListResponse getVehicleList(int pageNum, int pageSize, String statusFilter, long staleMillis) { + long now = System.currentTimeMillis(); + Set vehicleIds = cacheService.getKnownVehicleIds(); + List allVehicles = new ArrayList<>(); + + for (String vehicleId : vehicleIds) { + VehicleManagerCacheService.CacheEntry detailsEntry = cacheService.getVehicleDetails(vehicleId); + VehicleManagerCacheService.CacheEntry loginEntry = cacheService.getVehicleLoginStatus(vehicleId); + VehicleManagerCacheService.CacheEntry positionEntry = cacheService.getVehiclePosition(vehicleId); + VehicleManagerCacheService.CacheEntry chassisEntry = cacheService.getVehicleChassis(vehicleId); + VehicleManagerCacheService.CacheEntry suspendEntry = cacheService.getVehicleSuspend(vehicleId); + VehicleManagerCacheService.CacheEntry fmsEntry = cacheService.getVehicleFmsMessage(vehicleId); + VehicleManagerCacheService.CacheEntry orderEntry = cacheService.getVehicleOrder(vehicleId); + + String vehicleType = getText(detailsEntry != null ? detailsEntry.getData() : null, "vehicleType"); + String loginStatus = getText(loginEntry != null ? loginEntry.getData() : null, "loginStatus"); + boolean loginStale = isStale(loginEntry, now, staleMillis); + + String status; + if (loginEntry == null || loginStale) { + status = "offline"; + } else { + status = "login".equalsIgnoreCase(loginStatus) ? "online" : "offline"; + } + + boolean isEmergency = false; + if (!isStale(suspendEntry, now, staleMillis)) { + Integer suspendStatus = getInt(suspendEntry != null ? suspendEntry.getData() : null, "suspendStatus"); + if (suspendStatus != null && suspendStatus != 0) { + isEmergency = true; + status = "emergency"; + } + } + + boolean isFault = false; + if (!isStale(fmsEntry, now, staleMillis)) { + if (isFault(fmsEntry != null ? fmsEntry.getData() : null)) { + isFault = true; + status = "fault"; + } + } + + if (statusFilter != null && !statusFilter.isEmpty() && !status.equalsIgnoreCase(statusFilter)) { + continue; + } + + Map position = null; + if (positionEntry != null && positionEntry.getData() != null) { + JsonNode posData = positionEntry.getData(); + position = new HashMap<>(); + position.put("x", getDouble(posData, "x")); + position.put("y", getDouble(posData, "y")); + position.put("theta", getDouble(posData, "theta")); + } + + Double speed = null; + if (chassisEntry != null && chassisEntry.getData() != null) { + JsonNode chassisData = chassisEntry.getData(); + JsonNode stateInfo = chassisData.path("sys_info").path("state_info"); + speed = getDouble(stateInfo, "d_speed_kmph"); + } + + Double batteryLevel = null; + if (chassisEntry != null && chassisEntry.getData() != null) { + JsonNode chassisData = chassisEntry.getData(); + JsonNode stateInfo = chassisData.path("sys_info").path("state_info"); + String batteryStr = getText(stateInfo, "d_battery_available"); + if (batteryStr != null) { + try { + batteryLevel = Double.parseDouble(batteryStr); + } catch (NumberFormatException ignored) { + } + } + } + + String currentTask = null; + if (orderEntry != null && orderEntry.getData() != null) { + currentTask = getText(orderEntry.getData(), "businessKey"); + } + + VehicleListItemDTO item = VehicleListItemDTO.builder() + .vehicleId(vehicleId) + .vehicleType(vehicleType) + .status(status) + .position(position) + .speed(speed) + .batteryLevel(batteryLevel) + .lastSeenAt(getLastSeenAt(vehicleId)) + .isEmergency(isEmergency) + .isFault(isFault) + .currentTask(currentTask) + .build(); + + allVehicles.add(item); + } + + int total = allVehicles.size(); + int fromIndex = (pageNum - 1) * pageSize; + int toIndex = Math.min(fromIndex + pageSize, total); + List pagedVehicles = fromIndex < total ? + allVehicles.subList(fromIndex, toIndex) : new ArrayList<>(); + + VehicleSummary summary = getVehicleSummary(staleMillis); + + return VehicleListResponse.builder() + .total(total) + .pageNum(pageNum) + .pageSize(pageSize) + .rows(pagedVehicles) + .summary(summary) + .build(); + } + + private Double getDouble(JsonNode node, String field) { + if (node == null || node.isMissingNode()) { + return null; + } + JsonNode value = node.get(field); + if (value == null || value.isNull()) { + return null; + } + if (value.isDouble() || value.isFloat()) { + return value.asDouble(); + } + if (value.isInt() || value.isLong()) { + return (double) value.asLong(); + } + if (value.isTextual()) { + try { + return Double.parseDouble(value.asText()); + } catch (NumberFormatException ignored) { + return null; + } + } + return null; + } } diff --git a/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/VehicleStatusAggregationService.java b/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/VehicleStatusAggregationService.java index 036296e..bd4a91a 100644 --- a/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/VehicleStatusAggregationService.java +++ b/qaup-collision/src/main/java/com/qaup/collision/datacollector/service/VehicleStatusAggregationService.java @@ -61,8 +61,8 @@ public class VehicleStatusAggregationService { Double y = getDouble(data, "y"); if (x != null && y != null) { position = MotionStatusDTO.PositionDTO.builder() - .longitude(x) - .latitude(y) + .longitude(y) + .latitude(x) .build(); } Double theta = getDouble(data, "theta"); @@ -166,8 +166,8 @@ public class VehicleStatusAggregationService { Double y = getDouble(node, "y"); MissionContextDTO.WaypointDTO waypoint = MissionContextDTO.WaypointDTO.builder() .waypointId(String.valueOf(index++)) - .longitude(x) - .latitude(y) + .longitude(y) + .latitude(x) .status("PENDING") .build(); waypoints.add(waypoint);