diff --git a/admin/src/main/java/com/multictrl/common/constant/BusinessConstant.java b/admin/src/main/java/com/multictrl/common/constant/BusinessConstant.java index 7f8486c..d6f6a57 100644 --- a/admin/src/main/java/com/multictrl/common/constant/BusinessConstant.java +++ b/admin/src/main/java/com/multictrl/common/constant/BusinessConstant.java @@ -47,6 +47,8 @@ public interface BusinessConstant { String AIRPORT_ORGANIZATION_GET = "airport_organization_get"; String AIRPORT_ORGANIZATION_BIND = "airport_organization_bind"; String FLIGHT_TASK_RESOURCE_GET = "flighttask_resource_get"; + //私有协议,为了确认跳飞场景下,妙算pskd设备是否开启成功 + String PRIVATE_GET_MULTI_MIAOSUAN_PSDK_STATUS = "private_get_multi_miaosuan_psdk_status"; //********************************* dj events topic method *********************************// String FLIGHTTASK_PROGRESS = "flighttask_progress"; String TAKEOFF_TO_POINT_PROGRESS = "takeoff_to_point_progress"; diff --git a/admin/src/main/java/com/multictrl/modules/business/controller/RouteFlightController.java b/admin/src/main/java/com/multictrl/modules/business/controller/RouteFlightController.java index a70352a..35a04bb 100644 --- a/admin/src/main/java/com/multictrl/modules/business/controller/RouteFlightController.java +++ b/admin/src/main/java/com/multictrl/modules/business/controller/RouteFlightController.java @@ -25,13 +25,14 @@ import java.util.List; @RestController @RequestMapping("business/command") @Tag(name = "航线飞行", description = """ - 航线管理是无人机自主作业的重要功能, - 可以实现行业领域的批量化、智能化作业。 - 上云 API 提供了相关的接口,实现了航线任务在云端的共享查看、下发执行、取消以及进度上报等功能。 - 用户需要遵照航线文件格式规范(WPML)编写航线文件,定义航线任务。一个航线任务中可以定义多条航线。""") + 航线管理是无人机自主作业的重要功能, + 可以实现行业领域的批量化、智能化作业。 + 上云 API 提供了相关的接口,实现了航线任务在云端的共享查看、下发执行、取消以及进度上报等功能。 + 用户需要遵照航线文件格式规范(WPML)编写航线文件,定义航线任务。一个航线任务中可以定义多条航线。""") @ApiOrder(5) @RequiredArgsConstructor public class RouteFlightController { + private final DJIBaseService djiBaseService; private final RouteFlightService routeFlightService; @@ -76,7 +77,7 @@ public class RouteFlightController { @Operation(summary = "取消任务") @RequiresPermissions("bus:route:flight:flightTaskUndo") public Result flightTaskUndo(@PathVariable String dockSn, - @RequestBody List taskIds) { + @RequestBody List taskIds) { if (taskIds.isEmpty()) { return new Result<>().error(ErrorCode.PARAMS_ERROR); } @@ -89,7 +90,7 @@ public class RouteFlightController { @Operation(summary = "执行航线") @RequiresPermissions("bus:route:flight:flightExecute") public Result flightExecute(@PathVariable String dockSn, - @RequestBody FlightExecute flightExecute) { + @RequestBody FlightExecute flightExecute) { return new Result<>().ok(routeFlightService.flightExecute(dockSn, flightExecute, true)); } @@ -99,8 +100,8 @@ public class RouteFlightController { @Operation(summary = "空中下发航线") @RequiresPermissions("bus:route:flight:inFlightWaylineDeliver") public Result inFlightWaylineDeliver(@PathVariable String dockSn, - @Parameter(name = "routeId", description = "航线标识") - @RequestParam Long routeId) { + @Parameter(name = "routeId", description = "航线标识") + @RequestParam Long routeId) { return new Result<>().ok(routeFlightService.inFlightWaylineDeliver(dockSn, routeId)); } diff --git a/admin/src/main/java/com/multictrl/modules/business/dao/MultiGroupDao.java b/admin/src/main/java/com/multictrl/modules/business/dao/MultiGroupDao.java new file mode 100644 index 0000000..f490f97 --- /dev/null +++ b/admin/src/main/java/com/multictrl/modules/business/dao/MultiGroupDao.java @@ -0,0 +1,16 @@ +package com.multictrl.modules.business.dao; + +import com.multictrl.common.dao.BaseDao; +import com.multictrl.modules.business.entity.MultiGroupEntity; +import org.apache.ibatis.annotations.Mapper; + +/** + * 蛙跳组信息 + * + * @author 张闯 + * @since 2026-05-28 + */ +@Mapper +public interface MultiGroupDao extends BaseDao { + +} diff --git a/admin/src/main/java/com/multictrl/modules/business/dao/MultiGroupDeviceDao.java b/admin/src/main/java/com/multictrl/modules/business/dao/MultiGroupDeviceDao.java new file mode 100644 index 0000000..7325dc9 --- /dev/null +++ b/admin/src/main/java/com/multictrl/modules/business/dao/MultiGroupDeviceDao.java @@ -0,0 +1,16 @@ +package com.multictrl.modules.business.dao; + +import com.multictrl.common.dao.BaseDao; +import com.multictrl.modules.business.entity.MultiGroupDeviceEntity; +import org.apache.ibatis.annotations.Mapper; + +/** + * 蛙跳组绑定的设备信息 + * + * @author 张闯 + * @since 2026-05-28 + */ +@Mapper +public interface MultiGroupDeviceDao extends BaseDao { + +} diff --git a/admin/src/main/java/com/multictrl/modules/business/dto/DockDTO.java b/admin/src/main/java/com/multictrl/modules/business/dto/DockDTO.java index 7de0eee..a6d019c 100644 --- a/admin/src/main/java/com/multictrl/modules/business/dto/DockDTO.java +++ b/admin/src/main/java/com/multictrl/modules/business/dto/DockDTO.java @@ -55,6 +55,10 @@ public class DockDTO implements Serializable { @Schema(description = "机库型号") private String dockModel; + @NotBlank(message = "{dock.model.require}", groups = {AddGroup.class, UpdateGroup.class}) + @Schema(description = "使用场景") + private String scenario; + @NotNull(message = "{dept.id.require}", groups = {AddGroup.class, UpdateGroup.class}) @JsonProperty(required = true) @Schema(description = "所属部门") diff --git a/admin/src/main/java/com/multictrl/modules/business/dto/flight/FlightExecute.java b/admin/src/main/java/com/multictrl/modules/business/dto/flight/FlightExecute.java index 60bc4f8..c36561b 100644 --- a/admin/src/main/java/com/multictrl/modules/business/dto/flight/FlightExecute.java +++ b/admin/src/main/java/com/multictrl/modules/business/dto/flight/FlightExecute.java @@ -1,7 +1,9 @@ package com.multictrl.modules.business.dto.flight; +import com.multictrl.modules.business.dto.multi.PrivateMultiFlightBindDockInfo; import io.swagger.v3.oas.annotations.media.Schema; import jakarta.validation.constraints.NotNull; +import java.util.List; import lombok.Data; /** @@ -20,4 +22,9 @@ public class FlightExecute { @Schema(description = "模拟器执行") private FlightTaskPrepare.SimulateMission simulateMission; + + @Schema(hidden = true) + List privateMultiFlightBindDockInfos; + @Schema(hidden = true) + private String taskId; } diff --git a/admin/src/main/java/com/multictrl/modules/business/dto/flight/FlightTaskPrepare.java b/admin/src/main/java/com/multictrl/modules/business/dto/flight/FlightTaskPrepare.java index 13712e9..4e93bea 100644 --- a/admin/src/main/java/com/multictrl/modules/business/dto/flight/FlightTaskPrepare.java +++ b/admin/src/main/java/com/multictrl/modules/business/dto/flight/FlightTaskPrepare.java @@ -24,14 +24,14 @@ public class FlightTaskPrepare { //开始执行时间 // 任务开始执行时间毫秒时间戳。 // 可选字段。当 task_type 为 0 或 1 时必填,为 2 时非必填。 - private Long execute_time; + private long execute_time; //任务类型 //{"0":"立即任务","1":"定时任务","2":"条件任务"} //立即任务和定时任务均由execute_time指定执行时间; // 条件任务支持ready_conditions字段指定任务就绪条件,设 // 备可在指定时间段内满足就绪条件后即可执行; // 立即任务媒体上传优先级最高,定时任务和条件任务媒体上传优先级相同 - private Integer task_type; + private int task_type; //航线文件对象 private FileInfo file; //任务就绪条件 @@ -50,30 +50,30 @@ public class FlightTaskPrepare { private BreakPoint break_point; //返航高度 //{"max":1500,"min":20,"step":"","unit_name":"米 / m"} - private Integer rth_altitude; + private int rth_altitude; //返航高度模式 //{"0":"智能高度","1":"设定高度"} /// 智能返航模式下,飞行器将自动规划最佳返航高度。 /// 大疆机场当前不支持设置返航高度模式,只能选择'设定高度'模式。 /// 当环境,光线不满足视觉系统要求时(譬如傍晚阳光直射、夜间弱光无光), /// 飞行器将使用您设定的返航高度进行直线返航 - private Integer rth_mode; + private int rth_mode; //遥控器失控动作 //{"0":"返航","1":"悬停","2":"降落"} //失控动作,当前固定传的值是 0,即返航。 // 注意该枚举值定义跟飞控跟机场定义的不一致,机场端会进行转换。 - private Integer out_of_control_action; + private int out_of_control_action; //航线失控动作 //{"0":"继续执行航线任务","1":"退出航线任务,执行遥控器失控动作"} //保持跟 KMZ 文件一致 - private Integer exit_wayline_when_rc_lost; + private int exit_wayline_when_rc_lost; //航线精度类型 //{"0":"GPS 任务","1":"高精度 RTK 任务"} //高精度 RTK 任务:飞行器起飞后会在空中等待 RTK 收敛后再执行任务,等待 RTK 收敛的过程中无法暂停任务。 // 默认场景建议使用该模式。 // GPS 任务:飞行器无需等待 RTK 收敛便可以直接开始执行。 // 精度要求不高的任务或对起飞时效性要求较高的任务建议使用该模式。 - private Integer wayline_precision_type; + private int wayline_precision_type; //是否在模拟器中执行任务 //可选字段,用于在室内进行模拟任务调试。 //注意:进行模拟飞行前,请务必取下桨叶,以防舱盖关闭时夹断桨叶。 @@ -84,7 +84,7 @@ public class FlightTaskPrepare { // 值为0表示关闭,1表示开启。 // 飞行安全预先检查表示: 飞行器执行任务前,检查自身作业区文件是否与云端一致, // 如果不一致则拉取文件更新,如果一致则不处理 - private Integer flight_safety_advance_check; + private int flight_safety_advance_check; @Data @NoArgsConstructor @@ -92,18 +92,18 @@ public class FlightTaskPrepare { public static class BreakPoint { //断点序号 @Schema(description = "断点序号") - private Integer index; + private int index; //断点状态 //{"0":"在航段上","1":"在航点上"} - @Schema(description = "断点状态 {0:在航段上,1:在航点上}") - private Integer state; + @Schema(description = "断点状态 {\"0\":\"在航段上\",\"1\":\"在航点上\"}") + private int state; //当前航段进度 //{"max":"1.0","min":"0"} - @Schema(description = "当前航段进度 {max:1.0,min:0}") - private Double progress; + @Schema(description = "当前航段进度 {\"max\":\"1.0\",\"min\":\"0\"}") + private double progress; //航线 ID - @Schema(description = "wayline_id 航线 ID") - private Integer wayline_id; + @Schema(description = "航线 ID") + private int wayline_id; } @Data @@ -112,7 +112,7 @@ public class FlightTaskPrepare { public static class ExecutableConditions { //存储容量 //可执行任务的机场或飞行器最低存储容量,机场或飞行器存储容量不满足 storage_capacity 时,任务执行失败。 - private Integer storage_capacity; + private int storage_capacity; } @Data @@ -132,13 +132,13 @@ public class FlightTaskPrepare { public static class ReadyConditions { //电池容量 //可执行任务的飞行器电池电量百分比阈值,任务开始执行时的飞行器电量必须大于 battery_capacity。 - private Integer battery_capacity; + private int battery_capacity; //任务可执行时段的开始时间 //任务可执行时段起始时间毫秒时间戳,任务开始执行的时间必须大于 begin_time。 - private Long begin_time; + private long begin_time; //任务可执行时段的结束时间 //任务可执行时段截止时间毫秒时间戳,任务开始执行的时间必须小于 end_time。 - private Long end_time; + private long end_time; } @Data @@ -148,19 +148,19 @@ public class FlightTaskPrepare { //是否开启模拟器任务 //{"0":"不开启","1":"开启"} //当次任务打开或关闭模拟器 - @Schema(description = "is_enable 是否开启模拟器任务 {0:不开启,1:开启}") - private Integer is_enable; + @Schema(description = "是否开启模拟器任务 {\"0\":\"不开启\",\"1\":\"开启\"}") + private int is_enable; //纬度 //{"max":"90.0","min":"-90.0"} - @Schema(description = "机场纬度 {max:90.0,min:-90.0}") - private Double latitude; + @Schema(description = "机场纬度 {\"max\":\"90.0\",\"min\":\"-90.0\"}") + private double latitude; //经度 //{"max":"180.0","min":"-180.0"} - @Schema(description = "机场经度 {max:180.0,min:-180.0}") - private Double longitude; + @Schema(description = "机场经度 {\"max\":\"180.0\",\"min\":\"-180.0\"}") + private double longitude; //高度 //{"max":"9999.9","min":"-9999.9"unit_name":"米 / m"} - @Schema(description = "机场海拔高度{max:9999.9,min:-9999.9unit_name:米/m}") - private Double altitude; + @Schema(description = "机场海拔高度{\"max\":\"9999.9\",\"min\":\"-9999.9\"unit_name\":\"米 / m\"}") + private double altitude; } } diff --git a/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiDockDTO.java b/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiDockDTO.java new file mode 100644 index 0000000..61bf95d --- /dev/null +++ b/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiDockDTO.java @@ -0,0 +1,53 @@ +package com.multictrl.modules.business.dto.multi; + +import com.fasterxml.jackson.annotation.JsonProperty; +import io.swagger.v3.oas.annotations.media.Schema; +import lombok.Data; + +/** + * @author 张闯 + * @since 2026-05-28 + */ +@Schema(name = "蛙跳组绑定设备列表") +@Data +public class MultiDockDTO { + + @Schema(description = "主键") + private Long id; + + @JsonProperty(required = true) + @Schema(description = "机库名称") + private String dockName; + + @JsonProperty(required = true) + @Schema(description = "SN码") + private String dockSn; + + @JsonProperty(required = true) + @Schema(description = "机库类型") + private String dockType; + + @JsonProperty(required = true) + @Schema(description = "机库型号") + private String dockModel; + + @Schema(description = "使用场景") + private String scenario; + + @JsonProperty(required = true) + @Schema(description = "所属部门") + private Long deptId; + + @JsonProperty(required = true) + @Schema(description = "机场经度") + private double longitude; + + @JsonProperty(required = true) + @Schema(description = "机场纬度") + private double latitude; + + @JsonProperty(required = true) + @Schema(description = "机场椭球高度") + private double height; + +} diff --git a/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiGroupDTO.java b/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiGroupDTO.java new file mode 100644 index 0000000..15535b7 --- /dev/null +++ b/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiGroupDTO.java @@ -0,0 +1,36 @@ +package com.multictrl.modules.business.dto.multi; + +import com.fasterxml.jackson.annotation.JsonProperty; +import com.multictrl.common.validator.group.AddGroup; +import com.multictrl.common.validator.group.UpdateGroup; +import io.swagger.v3.oas.annotations.media.Schema; +import jakarta.validation.constraints.NotBlank; +import jakarta.validation.constraints.NotNull; +import jakarta.validation.constraints.Null; +import lombok.Data; + +/** + * @author 张闯 + * @since 2026-05-28 + */ + +@Data +@Schema(name = "蛙跳组信息") +public class MultiGroupDTO { + + /** + * 蛙跳组名称 + */ + @NotBlank(message = "{group.name.require}", groups = {AddGroup.class, UpdateGroup.class}) + @JsonProperty(required = true) + @Schema(description = "蛙跳组名称") + private String groupName; + /** + * 蛙跳组备注说明 + */ + @NotBlank(message = "{group.mark.require}", groups = {AddGroup.class, UpdateGroup.class}) + @JsonProperty(required = true) + @Schema(description = "蛙跳组备注说明") + private String groupMark; + +} diff --git a/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiGroupDeviceDTO.java b/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiGroupDeviceDTO.java new file mode 100644 index 0000000..1476db3 --- /dev/null +++ b/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiGroupDeviceDTO.java @@ -0,0 +1,34 @@ +package com.multictrl.modules.business.dto.multi; + +import com.fasterxml.jackson.annotation.JsonProperty; +import com.multictrl.common.validator.group.AddGroup; +import com.multictrl.common.validator.group.UpdateGroup; +import io.swagger.v3.oas.annotations.media.Schema; +import jakarta.validation.constraints.NotBlank; +import java.util.List; +import lombok.Data; + +/** + * @author 张闯 + * @since 2026-05-28 + */ +@Data +@Schema(name = "蛙跳组绑定设备列表") +public class MultiGroupDeviceDTO { + + /** + * 蛙跳组id + */ + @NotBlank(message = "{group.id.require}", groups = {AddGroup.class, UpdateGroup.class}) + @JsonProperty(required = true) + @Schema(description = "蛙跳组id") + private Long groudId; + /** + * 网关sn + */ + @NotBlank(message = "{gateway.sns.require}", groups = {AddGroup.class, UpdateGroup.class}) + @JsonProperty(required = true) + @Schema(description = "设备网关sn列表") + private List gatewaySns; + +} diff --git a/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiTaskDTO.java b/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiTaskDTO.java new file mode 100644 index 0000000..956a948 --- /dev/null +++ b/admin/src/main/java/com/multictrl/modules/business/dto/multi/MultiTaskDTO.java @@ -0,0 +1,25 @@ +package com.multictrl.modules.business.dto.multi; + +import io.swagger.v3.oas.annotations.media.Schema; +import java.util.List; +import lombok.Data; + +/** + * @author 张闯 + * @since 2026-05-31 + */ +@Data +@Schema(name = "蛙跳任务类") +public class MultiTaskDTO { + + List docks; + + MultiDockDTO miaoSuan; + + MultiDockDTO miaoSuanLocatedDock; + + String taskId; + + Long routeId; + +} diff --git a/admin/src/main/java/com/multictrl/modules/business/dto/multi/PrivateMultiFlightBindDockInfo.java b/admin/src/main/java/com/multictrl/modules/business/dto/multi/PrivateMultiFlightBindDockInfo.java new file mode 100644 index 0000000..a34afc4 --- /dev/null +++ b/admin/src/main/java/com/multictrl/modules/business/dto/multi/PrivateMultiFlightBindDockInfo.java @@ -0,0 +1,29 @@ +package com.multictrl.modules.business.dto.multi; + +import lombok.Data; + +/** + * aros 机场蛙跳参数 + * @author 张闯 + * @since 2026-05-31 + */ +@Data +public class PrivateMultiFlightBindDockInfo { + + private String dock_sn; + + private double longitude; + + private double latitude; + + private double height; + + private double alternate_land_point_longitude; + + private double alternate_land_point_latitude; + + private double alternate_land_point_height; + + private double alternate_land_point_safe_land_height; + +} diff --git a/admin/src/main/java/com/multictrl/modules/business/entity/DockEntity.java b/admin/src/main/java/com/multictrl/modules/business/entity/DockEntity.java index f5f2646..f1135ba 100644 --- a/admin/src/main/java/com/multictrl/modules/business/entity/DockEntity.java +++ b/admin/src/main/java/com/multictrl/modules/business/entity/DockEntity.java @@ -31,8 +31,19 @@ public class DockEntity extends BaseEntity { private String dockSn; /** * 机库类型 + * + * dock + * pilot + * miao_suan */ private String dockType; + /** + * 使用场景 + * null或者 inspection 巡检 + * multi 蛙跳 + */ + private String scenario; + /** * 机库型号 */ diff --git a/admin/src/main/java/com/multictrl/modules/business/entity/MultiGroupDeviceEntity.java b/admin/src/main/java/com/multictrl/modules/business/entity/MultiGroupDeviceEntity.java new file mode 100644 index 0000000..0240d58 --- /dev/null +++ b/admin/src/main/java/com/multictrl/modules/business/entity/MultiGroupDeviceEntity.java @@ -0,0 +1,33 @@ +package com.multictrl.modules.business.entity; + +import com.baomidou.mybatisplus.annotation.TableName; +import com.multictrl.common.entity.BaseEntity; +import java.util.Date; +import lombok.Data; +import lombok.EqualsAndHashCode; + +/** + * @author 张闯 + * @since 2026-05-28 + */ +@EqualsAndHashCode(callSuper = true) +@Data +@TableName("bus_multi_group_device") +public class MultiGroupDeviceEntity extends BaseEntity { + /** + * 蛙跳组id + */ + private Long groudId; + /** + * 网关sn + */ + private String gatewaySn; + /** + * 更新者 + */ + private Long updater; + /** + * 更新时间 + */ + private Date updateDate; +} diff --git a/admin/src/main/java/com/multictrl/modules/business/entity/MultiGroupEntity.java b/admin/src/main/java/com/multictrl/modules/business/entity/MultiGroupEntity.java new file mode 100644 index 0000000..90e7096 --- /dev/null +++ b/admin/src/main/java/com/multictrl/modules/business/entity/MultiGroupEntity.java @@ -0,0 +1,33 @@ +package com.multictrl.modules.business.entity; + +import com.baomidou.mybatisplus.annotation.TableName; +import com.multictrl.common.entity.BaseEntity; +import java.util.Date; +import lombok.Data; +import lombok.EqualsAndHashCode; + +/** + * @author 张闯 + * @since 2026-05-28 + */ +@EqualsAndHashCode(callSuper = true) +@Data +@TableName("bus_multi_group") +public class MultiGroupEntity extends BaseEntity { + + /** + * 蛙跳组名称 + */ + private String groupName; + /** + * 蛙跳组标识 + */ + private String groupMark; + /** + * 组织编号 + */ + private Long deptId; + + private Long updater; + private Date updateDate; +} diff --git a/admin/src/main/java/com/multictrl/modules/business/handler/OsdHandler.java b/admin/src/main/java/com/multictrl/modules/business/handler/OsdHandler.java index 87eb7f3..9961b45 100644 --- a/admin/src/main/java/com/multictrl/modules/business/handler/OsdHandler.java +++ b/admin/src/main/java/com/multictrl/modules/business/handler/OsdHandler.java @@ -58,13 +58,14 @@ public class OsdHandler implements MessageHandler { CacheUtils.set(BusinessConstant.DOCK_IN_WORK + dockSn, true); } //刚从“任务中”切到“空闲“,说明架次结束入库了 - if (modeCode == DockMode.IDLE.getCode() && CacheUtils.get(BusinessConstant.DOCK_IN_WORK + dockSn) != null) { + if (modeCode == DockMode.IDLE.getCode() + && CacheUtils.get(BusinessConstant.DOCK_IN_WORK + dockSn) != null) { CacheUtils.delete(BusinessConstant.DOCK_IN_WORK + dockSn); log.debug("{}机库架次飞行完成,取消DRC心跳", dockSn); List list = Optional.ofNullable(CacheUtils.get(BusinessConstant.DRC_HEART_BEAT_SN)) - .filter(obj -> obj instanceof List) - .map(obj -> (List) obj) - .orElse(Collections.emptyList()); + .filter(obj -> obj instanceof List) + .map(obj -> (List) obj) + .orElse(Collections.emptyList()); if (CollUtil.isNotEmpty(list)) { list.remove(dockSn); } @@ -85,9 +86,10 @@ public class OsdHandler implements MessageHandler { //保存osd到influxdb String latitude = data.getStr("latitude"); String longitude = data.getStr("longitude"); - if (latitude != null && longitude != null && !GPS_ZERO.equals(latitude) && !GPS_ZERO.equals(longitude)) { + if (latitude != null && longitude != null && !GPS_ZERO.equals(latitude) && !GPS_ZERO.equals( + longitude)) { String payload_index = data.getJSONArray("cameras") != null ? - data.getJSONArray("cameras").getJSONObject(0).getStr("payload_index") : null; + data.getJSONArray("cameras").getJSONObject(0).getStr("payload_index") : null; //获取电池电量,如果单电池则把 a赋值给b int capacity_percent_a; int capacity_percent_b; @@ -100,44 +102,48 @@ public class OsdHandler implements MessageHandler { } UavReport uavReport = UavReport.builder() - .dockSn(dockSn) - .obstacle_avoidance_horizon(data.getJSONObject("obstacle_avoidance").getInt("horizon")) - .obstacle_avoidance_upside(data.getJSONObject("obstacle_avoidance").getInt("upside")) - .obstacle_avoidance_downside(data.getJSONObject("obstacle_avoidance").getInt("downside")) - .is_near_area_limit(data.getInt("is_near_area_limit")) - .is_near_height_limit(data.getInt("is_near_height_limit")) - .payload_index(payload_index) - .gimbal_pitch(payload_index != null ? data.getJSONObject(payload_index).getDouble("gimbal_pitch") : null) - .gimbal_roll(payload_index != null ? data.getJSONObject(payload_index).getDouble("gimbal_roll") : null) - .gimbal_yaw(payload_index != null ? data.getJSONObject(payload_index).getDouble("gimbal_yaw") : null) - .zoom_factor(payload_index != null ? data.getJSONObject(payload_index).getDouble("zoom_factor") : null) - .track_id(data.getStr("track_id")) - .position_state_is_fixed(data.getJSONObject("position_state").getInt("is_fixed")) - .position_state_is_quality(data.getJSONObject("position_state").getInt("quality")) - .position_state_is_gps_number(data.getJSONObject("position_state").getInt("gps_number")) - .position_state_is_rtk_number(data.getJSONObject("position_state").getInt("rtk_number")) - .battery_capacity_percent(data.getJSONObject("battery").getInt("capacity_percent")) - .battery_remain_flight_time(data.getJSONObject("battery").getInt("remain_flight_time")) - .battery_return_home_power(data.getJSONObject("battery").getInt("return_home_power")) - .battery_landing_power(data.getJSONObject("battery").getInt("landing_power")) - .battery_capacity_percent_a(capacity_percent_a) - .battery_capacity_percent_b(capacity_percent_b) - .wind_direction(data.getInt("wind_direction")) - .wind_speed(data.getDouble("wind_speed")) - .home_distance(data.getDouble("home_distance")) - //state上报 + .dockSn(dockSn) + .obstacle_avoidance_horizon(data.getJSONObject("obstacle_avoidance").getInt("horizon")) + .obstacle_avoidance_upside(data.getJSONObject("obstacle_avoidance").getInt("upside")) + .obstacle_avoidance_downside(data.getJSONObject("obstacle_avoidance").getInt("downside")) + .is_near_area_limit(data.getInt("is_near_area_limit")) + .is_near_height_limit(data.getInt("is_near_height_limit")) + .payload_index(payload_index) + .gimbal_pitch( + payload_index != null ? data.getJSONObject(payload_index).getDouble("gimbal_pitch") : null) + .gimbal_roll( + payload_index != null ? data.getJSONObject(payload_index).getDouble("gimbal_roll") : null) + .gimbal_yaw( + payload_index != null ? data.getJSONObject(payload_index).getDouble("gimbal_yaw") : null) + .zoom_factor( + payload_index != null ? data.getJSONObject(payload_index).getDouble("zoom_factor") : null) + .track_id(data.getStr("track_id")) + .position_state_is_fixed(data.getJSONObject("position_state").getInt("is_fixed")) + .position_state_is_quality(data.getJSONObject("position_state").getInt("quality")) + .position_state_is_gps_number(data.getJSONObject("position_state").getInt("gps_number")) + .position_state_is_rtk_number(data.getJSONObject("position_state").getInt("rtk_number")) + .battery_capacity_percent(data.getJSONObject("battery").getInt("capacity_percent")) + .battery_remain_flight_time(data.getJSONObject("battery").getInt("remain_flight_time")) + .battery_return_home_power(data.getJSONObject("battery").getInt("return_home_power")) + .battery_landing_power(data.getJSONObject("battery").getInt("landing_power")) + .battery_capacity_percent_a(capacity_percent_a) + .battery_capacity_percent_b(capacity_percent_b) + .wind_direction(data.getInt("wind_direction")) + .wind_speed(data.getDouble("wind_speed")) + .home_distance(data.getDouble("home_distance")) + //state上报 // .home_latitude(data.getDouble("home_latitude")) // .home_longitude(data.getDouble("home_longitude")) - .attitude_head(data.getInt("attitude_head")) - .attitude_roll(data.getDouble("attitude_roll")) - .attitude_pitch(data.getDouble("attitude_pitch")) - .elevation(data.getDouble("elevation")) - .height(data.getDouble("height")) - .latitude(data.getDouble("latitude")) - .longitude(data.getDouble("longitude")) - .vertical_speed(data.getDouble("vertical_speed")) - .horizontal_speed(data.getDouble("horizontal_speed")) - .build(); + .attitude_head(data.getInt("attitude_head")) + .attitude_roll(data.getDouble("attitude_roll")) + .attitude_pitch(data.getDouble("attitude_pitch")) + .elevation(data.getDouble("elevation")) + .height(data.getDouble("height")) + .latitude(data.getDouble("latitude")) + .longitude(data.getDouble("longitude")) + .vertical_speed(data.getDouble("vertical_speed")) + .horizontal_speed(data.getDouble("horizontal_speed")) + .build(); influxService.addRecord(uavReport); } } diff --git a/admin/src/main/java/com/multictrl/modules/business/handler/RequestsHandler.java b/admin/src/main/java/com/multictrl/modules/business/handler/RequestsHandler.java index 05cfc56..4eeafcf 100644 --- a/admin/src/main/java/com/multictrl/modules/business/handler/RequestsHandler.java +++ b/admin/src/main/java/com/multictrl/modules/business/handler/RequestsHandler.java @@ -36,6 +36,7 @@ import java.util.List; @Component @RequiredArgsConstructor public class RequestsHandler implements MessageHandler { + private final DJIConfig djiConfig; private final MqttPushService mqttPushService; private final DockDeviceDao dockDeviceDao; @@ -74,7 +75,8 @@ public class RequestsHandler implements MessageHandler { return; } String sn = deviceJson.getStr("sn"); - DockDeviceEntity dockDevice = dockDeviceDao.selectOne(new QueryWrapper().eq("sn", sn)); + DockDeviceEntity dockDevice = dockDeviceDao.selectOne( + new QueryWrapper().eq("sn", sn)); if (dockDevice == null) { data.set("result", 1); mqttPushService.pushMessageByClient1(topic + BusinessConstant._REPLY, message.toString()); @@ -100,7 +102,8 @@ public class RequestsHandler implements MessageHandler { } else if (BusinessConstant.AIRPORT_ORGANIZATION_GET.equals(method)) {//第三步 查询设备绑定对应的组织信息 String deviceBindingCode = data.getStr("device_binding_code"); String organizationId = data.getStr("organization_id"); - if (!djiConfig.getDeviceBindCode().equals(deviceBindingCode) || !djiConfig.getOrganizationId().equals(organizationId)) { + if (!djiConfig.getDeviceBindCode().equals(deviceBindingCode) || !djiConfig.getOrganizationId() + .equals(organizationId)) { data.set("result", 2); mqttPushService.pushMessageByClient1(topic + BusinessConstant._REPLY, message.toString()); log.debug("requests step3--> 查询设备绑定对应的组织信息失败,设备绑定码或组织id不匹配"); @@ -143,9 +146,9 @@ public class RequestsHandler implements MessageHandler { device.setDeviceType(Integer.parseInt(split[1])); device.setSubType(Integer.parseInt(split[2])); DeviceDicEntity deviceDicEntity = deviceDicDao.selectOne(new QueryWrapper() - .eq("domain", device.getDomain()) - .eq("device_type", device.getDeviceType()) - .eq("sub_type", device.getSubType())); + .eq("domain", device.getDomain()) + .eq("device_type", device.getDeviceType()) + .eq("sub_type", device.getSubType())); device.setDeviceName(deviceDicEntity != null ? deviceDicEntity.getDeviceName() : "unknown"); bindDeviceList.add(device); } @@ -156,7 +159,7 @@ public class RequestsHandler implements MessageHandler { return; } dockDeviceDao.delete(new QueryWrapper().eq("sn", gateway).or() - .eq("parent_sn", gateway)); + .eq("parent_sn", gateway)); dockDeviceDao.insert(bindDeviceList); data.set("result", 0); mqttPushService.pushMessageByClient1(topic + BusinessConstant._REPLY, message.toString()); @@ -208,6 +211,19 @@ public class RequestsHandler implements MessageHandler { message.remove("gateway"); mqttPushService.pushMessageByClient1(topic + BusinessConstant._REPLY, message.toString()); log.debug("requests storage_config_get--> 存储配置获取成功"); + } else if (BusinessConstant.PRIVATE_GET_MULTI_MIAOSUAN_PSDK_STATUS.equals(method)) { + String psdkSn = message.getStr("psdk_sn"); + int status = CacheUtils.get(BusinessConstant.DOCK_OSD + psdkSn) != null ? 1 : 0; + data.clear(); + data.set("result", 0); + JSONObject output = new JSONObject(); + output.set("status", status); + data.set("output", output); + message.set("timestamp", System.currentTimeMillis()); + message.remove("need_reply"); + mqttPushService.pushMessageByClient1(topic + BusinessConstant._REPLY, message.toString()); + log.debug("requests private_get_multi_miaosuan_psdk_status--> 检查妙算设备是否上线:{}-> status: {}", + psdkSn, status); } } else { log.debug("requests --> payload解析失败,解析后为null"); diff --git a/admin/src/main/java/com/multictrl/modules/business/service/MqttPushService.java b/admin/src/main/java/com/multictrl/modules/business/service/MqttPushService.java index 388f2d9..cee4808 100644 --- a/admin/src/main/java/com/multictrl/modules/business/service/MqttPushService.java +++ b/admin/src/main/java/com/multictrl/modules/business/service/MqttPushService.java @@ -15,6 +15,7 @@ import org.springframework.stereotype.Component; @Slf4j @Component public class MqttPushService { + @Resource(name = "mqttOutboundChannel1") private MessageChannel mqttOutboundHandler1; @@ -22,7 +23,7 @@ public class MqttPushService { private MessageChannel mqttOutboundHandler2; /** - * 客户端1推送消息 + * 客户端1推送消息 该连接处理正常的协议交互 * * @param topic 主题 * @param msg 消息 @@ -30,11 +31,11 @@ public class MqttPushService { public void pushMessageByClient1(String topic, String msg) { log.debug("client1 down-> topic:{},msg:{}", topic, msg); mqttOutboundHandler1.send(MessageBuilder.withPayload(msg). - setHeader("mqtt_topic", topic).build()); + setHeader("mqtt_topic", topic).build()); } /** - * 客户端2推送消息 + * 客户端2推送消息 该连接处理drc控制的协议交互 * * @param topic 主题 * @param msg 消息 @@ -42,6 +43,6 @@ public class MqttPushService { public void pushMessageByClient2(String topic, String msg) { log.debug("client2 down-> topic:{},msg:{}", topic, msg); mqttOutboundHandler2.send(MessageBuilder.withPayload(msg). - setHeader("mqtt_topic", topic).build()); + setHeader("mqtt_topic", topic).build()); } } diff --git a/admin/src/main/java/com/multictrl/modules/business/service/MultiService.java b/admin/src/main/java/com/multictrl/modules/business/service/MultiService.java new file mode 100644 index 0000000..7c1ae52 --- /dev/null +++ b/admin/src/main/java/com/multictrl/modules/business/service/MultiService.java @@ -0,0 +1,35 @@ +package com.multictrl.modules.business.service; + +import com.multictrl.common.utils.Result; +import com.multictrl.modules.business.dto.multi.MultiDockDTO; +import com.multictrl.modules.business.dto.multi.MultiGroupDTO; +import com.multictrl.modules.business.dto.multi.MultiGroupDeviceDTO; +import com.multictrl.modules.business.dto.multi.MultiTaskDTO; +import com.multictrl.modules.business.entity.DockEntity; +import java.util.List; + +/** + * 阿罗斯机场 蛙跳 充电机库 Ars550 换电机库 Ars600 + * + * @author 张闯 + * @since 2026-05-28 + */ +public interface MultiService { + + List getDockList(); + + void saveMultiGroup(MultiGroupDTO multiGroupDTO); + + void saveMultiGroupDevice(MultiGroupDeviceDTO multiGroupDeviceDTO); + + void updateMultiGroup(MultiGroupDTO multiGroupDTO); + + void updateMultiGroupDevice(MultiGroupDeviceDTO multiGroupDeviceDTO); + + String privateMultiDockTaskFlightTaskCheck(MultiTaskDTO multiTaskDTO); + + String privateMultiDockFlightTaskOutbound(MultiTaskDTO multiTaskDTO); + + String privateMultiDockFlightTaskInbound(MultiTaskDTO multiTaskDTO); + +} diff --git a/admin/src/main/java/com/multictrl/modules/business/service/RouteFlightService.java b/admin/src/main/java/com/multictrl/modules/business/service/RouteFlightService.java index 245dd8c..6fe2d8d 100644 --- a/admin/src/main/java/com/multictrl/modules/business/service/RouteFlightService.java +++ b/admin/src/main/java/com/multictrl/modules/business/service/RouteFlightService.java @@ -2,6 +2,7 @@ package com.multictrl.modules.business.service; import com.multictrl.modules.business.dto.flight.FlightExecute; +import com.multictrl.modules.business.dto.multi.PrivateMultiFlightBindDockInfo; import java.util.List; /** diff --git a/admin/src/main/java/com/multictrl/modules/business/service/impl/DJIBaseServiceImpl.java b/admin/src/main/java/com/multictrl/modules/business/service/impl/DJIBaseServiceImpl.java index 580d46e..8b889d3 100644 --- a/admin/src/main/java/com/multictrl/modules/business/service/impl/DJIBaseServiceImpl.java +++ b/admin/src/main/java/com/multictrl/modules/business/service/impl/DJIBaseServiceImpl.java @@ -138,6 +138,7 @@ public class DJIBaseServiceImpl implements DJIBaseService { return message; } + @Override public String executeAndReturnResult(String dockSn, String method) { diff --git a/admin/src/main/java/com/multictrl/modules/business/service/impl/MultiServiceImpl.java b/admin/src/main/java/com/multictrl/modules/business/service/impl/MultiServiceImpl.java new file mode 100644 index 0000000..0b177b5 --- /dev/null +++ b/admin/src/main/java/com/multictrl/modules/business/service/impl/MultiServiceImpl.java @@ -0,0 +1,231 @@ +package com.multictrl.modules.business.service.impl; + +import cn.hutool.json.JSONObject; +import com.multictrl.common.constant.BusinessConstant; +import com.multictrl.common.exception.ErrorCode; +import com.multictrl.common.exception.RenException; +import com.multictrl.common.utils.CacheUtils; +import com.multictrl.common.utils.MessageUtils; +import com.multictrl.modules.business.dao.MultiGroupDao; +import com.multictrl.modules.business.dao.MultiGroupDeviceDao; +import com.multictrl.modules.business.dto.flight.FlightExecute; +import com.multictrl.modules.business.dto.multi.MultiDockDTO; +import com.multictrl.modules.business.dto.multi.MultiGroupDTO; +import com.multictrl.modules.business.dto.multi.MultiGroupDeviceDTO; +import com.multictrl.modules.business.dto.multi.MultiTaskDTO; +import com.multictrl.modules.business.dto.multi.PrivateMultiFlightBindDockInfo; +import com.multictrl.modules.business.service.DJIBaseService; +import com.multictrl.modules.business.service.MultiService; +import com.multictrl.modules.business.service.RouteFlightService; +import jakarta.annotation.Resource; +import java.util.ArrayList; +import java.util.List; +import lombok.extern.slf4j.Slf4j; +import org.springframework.stereotype.Service; + +/** + * 阿罗斯机场 蛙跳 + * + * @author 张闯 + * @since 2026-05-28 + */ +@Slf4j +@Service +public class MultiServiceImpl implements MultiService { + + @Resource + MultiGroupDao multiGroupDao; + @Resource + MultiGroupDeviceDao multiGroupDeviceDao; + @Resource + DJIBaseService djiBaseService; + @Resource + RouteFlightService routeFlightService; + + private static final String MIAO_SUAN = "miao_suan"; + + + @Override + public List getDockList() { + return List.of(); + } + + @Override + public void saveMultiGroup(MultiGroupDTO multiGroupDTO) { + + } + + @Override + public void saveMultiGroupDevice(MultiGroupDeviceDTO multiGroupDeviceDTO) { + + } + + @Override + public void updateMultiGroup(MultiGroupDTO multiGroupDTO) { + + } + + @Override + public void updateMultiGroupDevice(MultiGroupDeviceDTO multiGroupDeviceDTO) { + + } + + @Override + public String privateMultiDockTaskFlightTaskCheck(MultiTaskDTO multiTaskDTO) { + for (MultiDockDTO multiDockDTO : multiTaskDTO.getDocks()) { + if (multiDockDTO.getDockType().equals(MIAO_SUAN)) { + continue; + } + String result = privateMultiDockTaskFlightTaskCheck(multiDockDTO.getDockSn()); + log.info("privateMultiDockTaskFlightTaskCheck-> dockSn:{},result:{}", multiDockDTO.getDockSn(), result); + } + return MessageUtils.getMessage(ErrorCode.DOCK_EXEC_SUCCESS); + } + + @Override + public String privateMultiDockFlightTaskOutbound(MultiTaskDTO multiTaskDTO) { + //第一步,调用所有机场出库 + for (MultiDockDTO multiDockDTO : multiTaskDTO.getDocks()) { + if (multiDockDTO.getDockType().equals(MIAO_SUAN)) { + continue; + } + boolean need_drone_open = multiDockDTO.getDockSn() + .equals(multiTaskDTO.getMiaoSuanLocatedDock().getDockSn()); + String result = privateMultiDockFlightTaskOutbound(multiDockDTO.getDockSn(), + need_drone_open, multiTaskDTO.getMiaoSuan().getDockSn(), multiTaskDTO.getTaskId()); + log.info("privateMultiDockFlightTaskOutbound-> 调用所有机场出库 dockSn:{},result:{}", + multiDockDTO.getDockSn(), + result); + } + //第二步,检查机库各传感器状态,是否已经出库完成,180秒内 + int tryCount = 180; + while (tryCount-- > 0) { + boolean allFinished = true; + for (MultiDockDTO multiDockDTO : multiTaskDTO.getDocks()) { + if (multiDockDTO.getDockType().equals(MIAO_SUAN)) { + continue; + } + Object o; + if ((o = CacheUtils.get(BusinessConstant.DOCK_OSD + multiDockDTO.getDockSn())) == null) { + continue; + } + JSONObject jsonObject = (JSONObject) o; + //cover_state 舱盖状态 {"0":"关闭","1":"打开","2":"半开","3":"舱盖状态异常"} + int cover_state = jsonObject.getInt("cover_state"); + //putter_state 推杆状态 {"0":"关闭","1":"打开","2":"半开","3":"推杆状态异常"} + int putter_state = jsonObject.getInt("putter_state"); + log.info( + "privateMultiDockFlightTaskOutbound-> 检查机库各传感器状态,是否已经出库完成 dockSn:{},cover_state:{},putter_state:{}" + , multiDockDTO.getDockSn(), cover_state, putter_state); + allFinished = allFinished && cover_state == 1 && putter_state == 1; + } + if (allFinished) { + break; + } + } + if (tryCount <= 0) { + return "出库超时"; + } + //第三步,下发航线给psdk + FlightExecute flightExecute = new FlightExecute(); + flightExecute.setTaskId(multiTaskDTO.getTaskId()); + flightExecute.setRouteId(multiTaskDTO.getRouteId()); + //获取每个机库的 经纬度/高度/备降点经纬度/备降点高度 + List privateMultiFlightBindDockInfos = new ArrayList<>(); + for (MultiDockDTO multiDockDTO : multiTaskDTO.getDocks()) { + if (multiDockDTO.getDockType().equals(MIAO_SUAN)) { + continue; + } + Object o; + if ((o = CacheUtils.get(BusinessConstant.DOCK_OSD + multiDockDTO.getDockSn())) == null) { + throw new RenException("机库: " + multiDockDTO.getDockSn() + "信息获取失败"); + } + JSONObject jsonObject = (JSONObject) o; + PrivateMultiFlightBindDockInfo privateMultiFlightBindDockInfo = new PrivateMultiFlightBindDockInfo(); + privateMultiFlightBindDockInfo.setDock_sn(multiDockDTO.getDockSn()); + privateMultiFlightBindDockInfo.setLongitude(jsonObject.getDouble("longitude")); + privateMultiFlightBindDockInfo.setLatitude(jsonObject.getDouble("latitude")); + privateMultiFlightBindDockInfo.setHeight(jsonObject.getDouble("height")); + JSONObject alternate_land_point = jsonObject.getJSONObject("alternate_land_point"); + privateMultiFlightBindDockInfo.setAlternate_land_point_longitude( + alternate_land_point.getDouble("longitude")); + privateMultiFlightBindDockInfo.setAlternate_land_point_latitude(alternate_land_point.getDouble("latitude")); + privateMultiFlightBindDockInfo.setAlternate_land_point_height(alternate_land_point.getDouble("height")); + privateMultiFlightBindDockInfo.setAlternate_land_point_safe_land_height( + alternate_land_point.getDouble("safe_land_height")); + privateMultiFlightBindDockInfos.add(privateMultiFlightBindDockInfo); + } + flightExecute.setPrivateMultiFlightBindDockInfos(privateMultiFlightBindDockInfos); + + log.info("privateMultiDockFlightTaskOutbound-> 下发航线给妙算 flightExecute:{}", flightExecute); + return routeFlightService.flightExecute(multiTaskDTO.getMiaoSuan().getDockSn(), flightExecute); + } + + @Override + public String privateMultiDockFlightTaskInbound(MultiTaskDTO multiTaskDTO) { + //第一步,调用所有机场入库 + for (MultiDockDTO multiDockDTO : multiTaskDTO.getDocks()) { + if (multiDockDTO.getDockType().equals(MIAO_SUAN)) { + continue; + } + boolean need_drone_close = multiDockDTO.getDockSn() + .equals(multiTaskDTO.getMiaoSuanLocatedDock().getDockSn()); + String result = privateMultiDockFlightTaskInbound(multiDockDTO.getDockSn(), + need_drone_close, multiTaskDTO.getMiaoSuan().getDockSn(), multiTaskDTO.getTaskId()); + log.info("privateMultiDockFlightTaskInbound-> dockSn:{},result:{}", multiDockDTO.getDockSn(), + result); + } + //第二步,判断所有机场的门都关闭了 + int tryCount = 180; + while (tryCount-- > 0) { + boolean allFinished = true; + for (MultiDockDTO multiDockDTO : multiTaskDTO.getDocks()) { + if (multiDockDTO.getDockType().equals(MIAO_SUAN)) { + continue; + } + Object o; + if ((o = CacheUtils.get(BusinessConstant.DOCK_OSD + multiDockDTO.getDockSn())) == null) { + continue; + } + JSONObject jsonObject = (JSONObject) o; + //cover_state 舱盖状态 {"0":"关闭","1":"打开","2":"半开","3":"舱盖状态异常"} + int cover_state = jsonObject.getInt("cover_state"); + log.info( + "privateMultiDockFlightTaskInbound-> 检查机库各传感器状态,是否已经入库完成 dockSn:{},cover_state:{}" + , multiDockDTO.getDockSn(), cover_state); + allFinished = allFinished && cover_state == 0; + } + if (allFinished) { + break; + } + } + if (tryCount <= 0) { + return "入库超时"; + } + + return "流程结束"; + } + + private String privateMultiDockTaskFlightTaskCheck(String dockSn) { + return djiBaseService.executeAndReturnResult(dockSn, "private_multi_dock_task_flighttask_check"); + } + + private String privateMultiDockFlightTaskOutbound(String dockSn, boolean need_drone_open, String psdk_sn, + String task_id) { + JSONObject jsonObject = new JSONObject(); + jsonObject.set("need_drone_open", need_drone_open); + jsonObject.set("psdk_sn", psdk_sn); + jsonObject.set("task_id", task_id); + return djiBaseService.executeAndReturnResult(dockSn, "private_multi_doc_dask_flighttask_outbound", jsonObject); + } + + private String privateMultiDockFlightTaskInbound(String dockSn, boolean need_drone_close, String psdk_sn, + String task_id) { + JSONObject jsonObject = new JSONObject(); + jsonObject.set("need_drone_close", need_drone_close); + jsonObject.set("psdk_sn", psdk_sn); + jsonObject.set("task_id", task_id); + return djiBaseService.executeAndReturnResult(dockSn, "private_multi_doc_dask_flighttask_inbound", jsonObject); + } + +} diff --git a/admin/src/main/java/com/multictrl/modules/business/service/impl/RouteFlightServiceImpl.java b/admin/src/main/java/com/multictrl/modules/business/service/impl/RouteFlightServiceImpl.java index 2df40ea..58eb960 100644 --- a/admin/src/main/java/com/multictrl/modules/business/service/impl/RouteFlightServiceImpl.java +++ b/admin/src/main/java/com/multictrl/modules/business/service/impl/RouteFlightServiceImpl.java @@ -15,6 +15,7 @@ import com.multictrl.modules.business.dto.RouteDTO; import com.multictrl.modules.business.dto.flight.FlightExecute; import com.multictrl.modules.business.dto.flight.FlightTaskPrepare; import com.multictrl.modules.business.dto.flight.InFlightWaylineDeliver; +import com.multictrl.modules.business.dto.multi.PrivateMultiFlightBindDockInfo; import com.multictrl.modules.business.service.DJIBaseService; import com.multictrl.modules.business.service.FlightTaskService; import com.multictrl.modules.business.service.RouteFlightService; @@ -40,6 +41,7 @@ import java.util.concurrent.locks.ReentrantLock; @Service @RequiredArgsConstructor public class RouteFlightServiceImpl implements RouteFlightService { + private final DJIBaseService djiBaseService; private final RouteService routeService; private final MinioConfig minioConfig; @@ -53,14 +55,17 @@ public class RouteFlightServiceImpl implements RouteFlightService { return djiBaseService.executeAndReturnResult(dockSn, "flighttask_undo", data); } + /* + * multiFlightBindDockInfos aros机场蛙跳模式参数,把N个参与到蛙跳的的机场信息给到妙算,返航时,自动计算离哪个机库位置近,就降落到哪个机库 + */ @Override - public String flightExecute(String dockSn, FlightExecute flightExecute, Boolean isRecord) { + public String flightExecute(String dockSn, FlightExecute flightExecute) { ReentrantLock lock = cacheLock.computeIfAbsent(dockSn, k -> new ReentrantLock()); lock.lock(); try { Boolean dockOnline = djiBaseService.isDockOnline(dockSn); if (!dockOnline) { - throw new RenException(ErrorCode.DOCK_OSD_NOT_EXIST, "无法操作"); + throw new RenException(ErrorCode.DOCK_OSD_NOT_EXIST, "机场不在线,无法操作"); } Integer dockModeCode = djiBaseService.getDockModeCode(dockSn); if (!Objects.equals(DockMode.IDLE.getCode(), dockModeCode)) { @@ -73,6 +78,9 @@ public class RouteFlightServiceImpl implements RouteFlightService { } //任务标识 String taskId = IdUtil.fastSimpleUUID(); + if (StrUtil.isNotEmpty(flightExecute.getTaskId())) { + taskId = flightExecute.getTaskId(); + } CacheUtils.set(BusinessConstant.WORKING_TASK_ID + dockSn, taskId); //设置默认相机模式,需要定频推送前端 CacheUtils.set(BusinessConstant.UAV_VIDEO_TYPE + dockSn, "wide"); @@ -104,27 +112,24 @@ public class RouteFlightServiceImpl implements RouteFlightService { flightTaskPrepare.setFile(fileInfo); //获取断点,如果断点续飞请设置 // flightTaskPrepare.setBreak_point(null); - flightTaskPrepare.setRth_mode(1); flightTaskPrepare.setRth_altitude((int) Math.round(globalRthHeight)); - //{"0":"返航","1":"悬停","2":"降落"} - //失控动作,当前固定传的值是 0,即返航。注意该枚举值定义跟飞控跟机场定义的不一致,机场端会进行转换。 - flightTaskPrepare.setOut_of_control_action(0); flightTaskPrepare.setExit_wayline_when_rc_lost(exitOnRcLost); - //{"0":"GPS 任务","1":"高精度 RTK 任务"} - flightTaskPrepare.setWayline_precision_type(1); //模拟器执行 if (flightExecute.getSimulateMission() != null) { flightTaskPrepare.setSimulate_mission(flightExecute.getSimulateMission()); } + if (flightExecute.getPrivateMultiFlightBindDockInfos() != null) { + flightTaskPrepare.setPrivate_multi_flight_bind_dock_info( + flightExecute.getPrivateMultiFlightBindDockInfos()); + } JSONObject data = JsonUtils.parseObject(JsonUtils.toJsonString(flightTaskPrepare), JSONObject.class); String result = djiBaseService.executeAndReturnResult(dockSn, "flighttask_prepare", data); log.debug("flight_task_prepare --> result:{}", result); //执行任务 Utils.sleep(1000); - String resultMsg = djiBaseService.executeAndReturnResult(dockSn, "flighttask_execute", new JSONObject().set("flight_id", taskId)); - if (isRecord) { - flightTaskService.addRouteTask(taskId, dockSn, route.getId()); - } + String resultMsg = djiBaseService.executeAndReturnResult(dockSn, "flighttask_execute", + new JSONObject().set("flight_id", taskId)); + flightTaskService.addRouteTask(taskId, dockSn, route.getId()); return resultMsg; } finally { Utils.sleep(2000); @@ -184,7 +189,8 @@ public class RouteFlightServiceImpl implements RouteFlightService { if (flightId == null) { throw new RenException(ErrorCode.ROUTE_TASK_NOT_EXIST); } - return djiBaseService.executeAndReturnResult(dockSn, "in_flight_wayline_stop", new JSONObject().set("in_flight_wayline_id", flightId)); + return djiBaseService.executeAndReturnResult(dockSn, "in_flight_wayline_stop", + new JSONObject().set("in_flight_wayline_id", flightId)); } @Override @@ -193,6 +199,7 @@ public class RouteFlightServiceImpl implements RouteFlightService { if (flightId == null) { throw new RenException(ErrorCode.ROUTE_TASK_NOT_EXIST); } - return djiBaseService.executeAndReturnResult(dockSn, "in_flight_wayline_recover", new JSONObject().set("in_flight_wayline_id", flightId)); + return djiBaseService.executeAndReturnResult(dockSn, "in_flight_wayline_recover", + new JSONObject().set("in_flight_wayline_id", flightId)); } } diff --git a/admin/src/main/resources/application-docker.yml b/admin/src/main/resources/application-docker.yml index f65a586..80a7f4c 100644 --- a/admin/src/main/resources/application-docker.yml +++ b/admin/src/main/resources/application-docker.yml @@ -78,6 +78,6 @@ influx: org: dj host: - ip: 223.108.157.174 + ip: 192.168.1.193 port: 61620 is-ssl: false \ No newline at end of file diff --git a/pom.xml b/pom.xml index 5a77ff0..e86b753 100644 --- a/pom.xml +++ b/pom.xml @@ -8,8 +8,20 @@ Dock-MultiCtrl 大疆机场多版本控制 + + + + org.apache.maven.plugins + maven-compiler-plugin + + 7 + 7 + + + + - + org.springframework.boot spring-boot-starter-parent 4.0.5 @@ -106,6 +118,11 @@ springdoc-openapi-starter-webmvc-ui ${springdoc.version} + + com.alibaba.fastjson2 + fastjson2 + 2.0.62 +