package com.kym.miniapp.jobs;

import com.alibaba.fastjson2.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.kym.common.utils.CommUtil;
import com.kym.entity.common.RedisKeys;
import com.kym.entity.miniapp.ChargeOrder;
import com.kym.service.miniapp.ChargeOrderService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

import java.time.LocalTime;
import java.util.ArrayList;

/**
 * @author skyline
 * 设备充电状态信息（订单信息）更新定时任务
 * 2024-08-12
 */
@Component
@Slf4j
public class EquipmentChargeStatusJob {

    private final StringRedisTemplate redisTemplate;
    private final ChargeOrderService chargeOrderService;

    public EquipmentChargeStatusJob(StringRedisTemplate redisTemplate, ChargeOrderService chargeOrderService) {
        this.redisTemplate = redisTemplate;
        this.chargeOrderService = chargeOrderService;
    }

    // 每5分钟执行一次，但在00:00:00-06:30:00期间不执行
    @Scheduled(cron = "0 0/5 * * * ?")
    public void executeMpUserRelationJob() {
        // 判断当前时间是否在00:00:00-06:30:00之间
        var now = LocalTime.now();
        if (now.isAfter(LocalTime.of(0, 0, 0)) && now.isBefore(LocalTime.of(6, 30, 0))) {
            return;
        }
        performTask();
    }

    // 在00:00:00-06:30:00期间每隔30分钟执行一次
    @Scheduled(cron = "0 0/30 * * * ?")
    public void executeMpUserRelationJobInEarlyMorning() {
        // 判断当前时间是否在00:00:00-00:06:30之间
        var now = LocalTime.now();
        if (now.isAfter(LocalTime.of(6, 30, 0)) && now.isBefore(LocalTime.of(23, 59, 59))) {
            return;
        }

        performTask();
    }




    void performTask() {
        log.info("设备充电状态信息（订单信息）更新定时任务启动...");
        var orders = redisTemplate.opsForHash().values(RedisKeys.CHARGE_ORDER_EQUIP_CHARGE_STATUS);
        if (CommUtil.isNotEmptyAndNull(orders)) {
            // 实际已结束订单
            var orderList = new ArrayList<ChargeOrder>();
            orders.forEach(order -> {
                var chargeOrder = JSONObject.parseObject(order.toString(), ChargeOrder.class);
                // 检查DB中该订单的当前状态，防止用Redis脏数据覆盖已结束的订单
                var dbOrder = chargeOrderService.lambdaQuery()
                        .eq(ChargeOrder::getStartChargeSeq, chargeOrder.getStartChargeSeq())
                        .select(ChargeOrder::getChargeStatus, ChargeOrder::getOrderStatus)
                        .one();
                if (dbOrder != null && (dbOrder.getChargeStatus().equals(ChargeOrder.CHARGE_STATUS_已结束) || dbOrder.getOrderStatus().equals(ChargeOrder.ORDER_STATUS_成功))) {
                    log.info("订单{}已在DB中结束，跳过Redis数据覆盖，清理Redis缓存", chargeOrder.getStartChargeSeq());
                    redisTemplate.opsForHash().delete(RedisKeys.CHARGE_ORDER_EQUIP_CHARGE_STATUS, chargeOrder.getStartChargeSeq());
                    return;
                }
                orderList.add(chargeOrder);
                if (chargeOrder.getChargeStatus().equals(ChargeOrder.CHARGE_STATUS_停止中) || chargeOrder.getChargeStatus().equals(ChargeOrder.CHARGE_STATUS_已结束)) {
                    redisTemplate.opsForHash().delete(RedisKeys.CHARGE_ORDER_EQUIP_CHARGE_STATUS, chargeOrder.getStartChargeSeq());
                }
            });
            if (!orderList.isEmpty()) {
                chargeOrderService.updateBatchByQueryWrapper(orderList, order ->
                        new QueryWrapper<ChargeOrder>().eq("start_charge_seq", order.getStartChargeSeq())
                                .ne("charge_status", ChargeOrder.CHARGE_STATUS_已结束)
                                .ne("order_status", ChargeOrder.ORDER_STATUS_成功));
            }
        }
        log.info("设备充电状态信息（订单信息）更新定时任务结束，本次更新{}条订单...", orders.size());
    }


}
