package com.multictrl.modules.business.q20.handler;

import cn.hutool.json.JSONObject;
import com.multictrl.common.constant.BusinessConstant;
import com.multictrl.common.utils.CacheUtils;
import com.multictrl.common.utils.JsonUtils;
import com.multictrl.modules.business.handler.MessageHandler;
import com.multictrl.modules.business.q20.influxdb.Q20OsdReport;
import com.multictrl.modules.business.service.FlightTaskService;
import com.multictrl.modules.business.service.InfluxService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;

/**
 * Q20基础遥测数据处理（method: osd）
 * 定频上报飞行数据：longitude, latitude, height, altitude, vs, gs, heading,
 * pitch, roll, battery, voltage, mode, flying, fly_time, fly_distance, home_location, state等
 *
 * @author 938693313@qq.com
 * @since 1.0.0 2026/5/12
 */
@Slf4j
@Component
@RequiredArgsConstructor
public class Q20OsdHandler implements MessageHandler {

    private final FlightTaskService flightTaskService;
    private final InfluxService influxService;

    @Override
    public void handleMessage(String topic, String payload, String gateway) {
        JSONObject message = JsonUtils.parseObject(payload, JSONObject.class);
        if (message != null) {
            String deviceSn = message.getStr(BusinessConstant.GATEWAY);
            JSONObject data = message.getJSONObject(BusinessConstant.DATA);
            if (data != null) {
                CacheUtils.set(Q20Constant.Q20_OSD + deviceSn, data);
                trackFlyingState(deviceSn, data);
                saveToInflux(deviceSn, data);
            }
        } else {
            log.debug("Q20 osd --> payload解析失败，解析后为null");
        }
    }

    private void trackFlyingState(String deviceSn, JSONObject data) {
        Integer flying = data.getInt("flying");
        if (flying == null) {
            return;
        }
        // 起飞中，首次检测到飞行状态时更新架次开始
        if (flying == 1) {
            if (CacheUtils.get(Q20Constant.Q20_IN_WORK + deviceSn) == null) {
                flightTaskService.updateTaskStart(deviceSn);
                log.debug("{}设备架次开始，更新架次表", deviceSn);
            }
            CacheUtils.set(Q20Constant.Q20_IN_WORK + deviceSn, true);
        }
        // 刚从飞行切到非飞行，架次结束
        if (flying == 0 && CacheUtils.get(Q20Constant.Q20_IN_WORK + deviceSn) != null) {
            CacheUtils.delete(Q20Constant.Q20_IN_WORK + deviceSn);
            flightTaskService.updateTaskComplete(deviceSn);
            log.debug("{}设备架次结束，更新架次表", deviceSn);
        }
    }

    private void saveToInflux(String deviceSn, JSONObject data) {
        Double longitude = data.getDouble("longitude");
        Double latitude = data.getDouble("latitude");
        if (longitude == null || latitude == null || longitude == 0 || latitude == 0) {
            return;
        }
        JSONObject homeLocation = data.getJSONObject("home_location");
        JSONObject state = data.getJSONObject("state");

        Q20OsdReport report = Q20OsdReport.builder()
                .deviceSn(deviceSn)
                .order_id(data.getStr("order_id"))
                .longitude(longitude)
                .latitude(latitude)
                .height(data.getFloat("height"))
                .altitude(data.getFloat("altitude"))
                .vs(data.getFloat("vs"))
                .gs(data.getFloat("gs"))
                .heading(data.getFloat("heading"))
                .pitch(data.getFloat("pitch"))
                .roll(data.getFloat("roll"))
                .battery(data.getInt("battery"))
                .voltage(data.getInt("voltage"))
                .mode(data.getStr("mode"))
                .flying(data.getInt("flying"))
                .fly_time(data.getLong("fly_time"))
                .fly_distance(data.getFloat("fly_distance"))
                .home_set(data.getInt("home_set"))
                .home_distance(data.getFloat("home_distance"))
                .home_altitude(homeLocation != null ? homeLocation.getFloat("altitude") : null)
                .home_latitude(homeLocation != null ? homeLocation.getFloat("latitude") : null)
                .home_longitude(homeLocation != null ? homeLocation.getFloat("longitude") : null)
                .state_safe_enabled(state != null ? state.getInt("safe_enabled") : null)
                .state_rtk_enabled(state != null ? state.getInt("rtk_enabled") : null)
                .state_rtk_connected(state != null ? state.getInt("rtk_connected") : null)
                .state_rc_connected(state != null ? state.getInt("rc_connected") : null)
                .state_obs_enabled(state != null ? state.getInt("obs_enabled") : null)
                .state_accel_cal(state != null ? state.getInt("accel_cal") : null)
                .state_gyro_cal(state != null ? state.getInt("gyro_cal") : null)
                .state_hor_cal(state != null ? state.getInt("hor_cal") : null)
                .state_mag_cal(state != null ? state.getInt("mag_cal") : null)
                .state_fpv_live(state != null ? state.getInt("fpv_live") : null)
                .state_stream_live(state != null ? state.getInt("stream_live") : null)
                .build();
        influxService.addRecord(report);
    }
}
