pom.xml
@@ -197,7 +197,10 @@ <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-aop</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-amqp</artifactId> </dependency> </dependencies> <build> src/main/java/com/dji/sample/component/mqtt/handler/InboundMessageRouter.java
@@ -3,7 +3,9 @@ import com.dji.sample.common.util.SpringBeanUtils; import com.dji.sample.component.mqtt.model.ChannelName; import com.dji.sample.component.mqtt.model.DeviceTopicEnum; import com.dji.sample.component.rabbitmq.config.MqttMsgProxyProducer; import lombok.extern.slf4j.Slf4j; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.integration.annotation.Router; import org.springframework.integration.mqtt.support.MqttHeaders; import org.springframework.integration.router.AbstractMessageRouter; @@ -24,6 +26,8 @@ @Component @Slf4j public class InboundMessageRouter extends AbstractMessageRouter { @Autowired private MqttMsgProxyProducer mqttMsgProxyProducer; /** * All mqtt broker messages will arrive here before distributing them to different channels. @@ -41,7 +45,12 @@ DeviceTopicEnum topicEnum = DeviceTopicEnum.find(topic); MessageChannel bean = (MessageChannel) SpringBeanUtils.getBean(topicEnum.getBeanName()); String msg = new String(payload); try { mqttMsgProxyProducer.publish(topic.replace("/","."), msg); } catch (Exception e) { log.error("消息发送失败:", e); } return Collections.singleton(bean); } } src/main/java/com/dji/sample/component/rabbitmq/config/MqttMsgProxyProducer.java
New file @@ -0,0 +1,56 @@ package com.dji.sample.component.rabbitmq.config; import org.springframework.amqp.core.Message; import org.springframework.amqp.core.MessageBuilder; import org.springframework.amqp.core.TopicExchange; import org.springframework.amqp.rabbit.core.RabbitTemplate; import org.springframework.amqp.support.converter.Jackson2JsonMessageConverter; import org.springframework.amqp.support.converter.MessageConverter; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Bean; import org.springframework.stereotype.Component; import java.util.Date; @Component public class MqttMsgProxyProducer { @Autowired private RabbitTemplate rabbitTemplate; private static final String EXCHANGE_NAME = "mshub.uav"; @Bean(EXCHANGE_NAME) public TopicExchange createExchange(){ return new TopicExchange(EXCHANGE_NAME,true,false); } public void publish_test() { // String message = new Date() + "Beijing"; Message message = MessageBuilder.withBody("hello javaboy".getBytes()) .setExpiration("10000") .build(); System.out.println("生产者产生消息=====" + message); rabbitTemplate.convertAndSend(EXCHANGE_NAME,"rabbitmq_queue", message); } public void publish(String routingKey, Object content) { rabbitTemplate.convertAndSend(EXCHANGE_NAME,routingKey, content); } public void publish(String routingKey, String content) { Message message = MessageBuilder.withBody(content.getBytes()) .setExpiration("1000") .build(); rabbitTemplate.send(EXCHANGE_NAME,routingKey, message); } /** * 使用json序列化机制,进行消息转换 * @return - */ @Bean public MessageConverter jackson2MessageConverter() { return new Jackson2JsonMessageConverter(); } } src/main/java/com/dji/sample/log/dao/IDroneFlightLogMapper.java
@@ -2,6 +2,11 @@ import com.baomidou.mybatisplus.core.mapper.BaseMapper; import com.dji.sample.log.model.entity.DroneFlightLogEntity; import com.dji.sample.wayline.model.dto.WaylineJobCountDTO; import com.dji.sample.wayline.model.entity.WaylineJobEntity; import org.apache.ibatis.annotations.Param; import java.util.List; /** * @PROJECT_NAME: iot_drone_api @@ -10,4 +15,6 @@ * @DATE: 2023/10/27 17:53 */ public interface IDroneFlightLogMapper extends BaseMapper<DroneFlightLogEntity> { List<DroneFlightLogEntity> patrolStatistics(@Param("workspaceId") String workspaceId, @Param("queryTime") String queryTime); } src/main/java/com/dji/sample/log/dao/IDroneFlightLogMapper.xml
New file @@ -0,0 +1,16 @@ <?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.dji.sample.log.dao.IDroneFlightLogMapper"> <select id="patrolStatistics" resultType="com.dji.sample.log.model.entity.DroneFlightLogEntity"> SELECT fl.* FROM drone_flight_log fl WHERE 1=1 <if test="queryTime != null and queryTime != ''"> and ( FROM_UNIXTIME( fl.end_time / 1000, '%Y' ) = #{queryTime} OR FROM_UNIXTIME( fl.end_time / 1000, '%Y-%m' ) =#{queryTime}) </if> <if test="workspaceId != null and workspaceId != ''"> and fl.workspace_id = #{workspaceId} </if> ORDER BY fl.end_time DESC </select> </mapper> src/main/java/com/dji/sample/log/model/entity/DroneFlightLogEntity.java
@@ -38,5 +38,8 @@ private Long startTime; @TableField(value = "end_time", fill = FieldFill.INSERT_UPDATE) private Long endTime; @TableField("total_flight_distance") private Double totalFlightDistance; @TableField("track_id") private String trackId; } src/main/java/com/dji/sample/log/model/entity/DroneFlightLogInfoEntity.java
@@ -31,5 +31,9 @@ private Double longitude; @TableField(value = "create_time", fill = FieldFill.INSERT) private Long createTime; @TableField("height") private Double height; @TableField("elevation") private Double elevation; } src/main/java/com/dji/sample/manage/model/receiver/OsdSubDeviceReceiver.java
@@ -81,4 +81,6 @@ private Integer totalFlightSorties; private WaylineRcLostActionEnum exitWaylineWhenRcLost; private String trackId; } src/main/java/com/dji/sample/manage/service/impl/DeviceOSDServiceImpl.java
@@ -88,6 +88,7 @@ .workspaceId(device.getWorkspaceId()) .title(data.getModeCode().getVal() == 3?"手动飞行":data.getModeCode().getVal() == 4?"自动起飞":data.getModeCode().getVal() == 5?"航线飞行":"未知") .startTime(System.currentTimeMillis()) .trackId(data.getTrackId()) .build(); droneFlightLogService.save(dflPo); //缓存对象用于关联数据 @@ -102,6 +103,7 @@ DroneFlightLogEntity dflPo = (DroneFlightLogEntity) RedisOpsUtils.get(RedisConst.FLIGHT_LOG + device.getDeviceSn()); dflPo.setEndTime(System.currentTimeMillis()); dflPo.setTotalFlightDistance(data.getTotalFlightDistance()); droneFlightLogService.update(dflPo); RedisOpsUtils.del(RedisConst.FLIGHT_LOG + device.getDeviceSn()); @@ -116,6 +118,8 @@ .latitude(data.getLatitude()) .longitude(data.getLongitude()) .flightId(dflPo.getId()) .height(data.getHeight()) .elevation(data.getElevation()) .build(); droneFlightLogInfoService.save(dfliPo); } src/main/java/com/dji/sample/wayline/model/dto/WaylineJobCountDTO.java
@@ -5,6 +5,7 @@ @Data public class WaylineJobCountDTO { private Integer totalNumber; private Integer totalTime; private String totalDuration; private Integer totalDistance; } src/main/java/com/dji/sample/wayline/service/impl/WaylineJobServiceImpl.java
@@ -5,6 +5,7 @@ import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper; import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.extension.conditions.query.LambdaQueryChainWrapper; import com.baomidou.mybatisplus.extension.conditions.update.LambdaUpdateChainWrapper; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.dji.sample.common.error.CommonErrorEnum; @@ -25,6 +26,8 @@ import com.dji.sample.control.service.IControlService; import com.dji.sample.control.service.IDrcService; import com.dji.sample.geo.entity.GeoJson; import com.dji.sample.log.dao.IDroneFlightLogMapper; import com.dji.sample.log.model.entity.DroneFlightLogEntity; import com.dji.sample.manage.model.dto.DeviceDTO; import com.dji.sample.manage.model.enums.DeviceModeCodeEnum; import com.dji.sample.manage.model.enums.DockModeCodeEnum; @@ -105,6 +108,9 @@ @Autowired private IControlService controlService; @Autowired private IDroneFlightLogMapper flightLogMapper; private Optional<WaylineJobDTO> insertWaylineJob(WaylineJobEntity jobEntity) { int id = mapper.insert(jobEntity); @@ -896,16 +902,23 @@ @Override public WaylineJobCountDTO patrolStatistics(String workspaceId, String queryTime) { WaylineJobCountDTO waylineJobCountDTO = new WaylineJobCountDTO(); List<WaylineJobEntity> list = mapper.patrolStatistics(workspaceId, queryTime); List<DroneFlightLogEntity> list = flightLogMapper.patrolStatistics(workspaceId,queryTime); if (!CollectionUtils.isEmpty(list)) { waylineJobCountDTO.setTotalNumber(list.size()); long totalTime = list.stream().filter(task -> task.getCompletedTime()!= null && task.getExecuteTime()!= null).mapToLong(s -> s.getCompletedTime() - s.getExecuteTime()).sum() / 1000; StringBuffer buffer = new StringBuffer(); long totalTime = list.stream().filter(task -> task.getEndTime()!= null && task.getStartTime()!= null).mapToLong(s -> s.getEndTime() - s.getStartTime()).sum() / 1000; long h = totalTime / 3600; long m = (totalTime % 3600) / 60; buffer.append(h).append(" h "); buffer.append(m).append(" min"); waylineJobCountDTO.setTotalDuration(buffer.toString()); waylineJobCountDTO.setTotalDuration( String.format("%02d h %02d min", h, m)); List<String> deviceSn = list.stream().map(DroneFlightLogEntity::getDeviceSn).distinct().collect(Collectors.toList()); double sum = 0.0; for (String sn : deviceSn) { Double totalFlightDistance = new LambdaQueryChainWrapper<>(flightLogMapper) .eq(DroneFlightLogEntity::getDeviceSn, sn).orderByDesc(DroneFlightLogEntity::getEndTime).last("limit 1").one().getTotalFlightDistance(); if (totalFlightDistance!= null){ sum+=totalFlightDistance; } } waylineJobCountDTO.setTotalDistance((int) sum); } return waylineJobCountDTO; } src/main/resources/application.yml
@@ -37,6 +37,18 @@ multipart: max-file-size: 2GB max-request-size: 2GB # rabbitmq: # host: 182.106.212.58 # port: 25672 # username: root # password: root # virtualHost: / # rabbitmq: # host: localhost # port: 5672 # username: guest # password: guest # virtualHost: / jwt: issuer: DJI