package com.ycwl.basic.task;

import cn.hutool.core.date.DateUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.ycwl.basic.integration.scenic.dto.scenic.ScenicV2DTO;
import com.ycwl.basic.mapper.MemberMapper;
import com.ycwl.basic.model.pc.member.resp.MemberRespVO;
import com.ycwl.basic.model.pc.notify.req.WechatSubscribeNotifyTriggerRequest;
import com.ycwl.basic.pricing.entity.PriceCouponClaimRecord;
import com.ycwl.basic.pricing.entity.PriceCouponConfig;
import com.ycwl.basic.pricing.enums.CouponStatus;
import com.ycwl.basic.pricing.mapper.PriceCouponClaimRecordMapper;
import com.ycwl.basic.pricing.mapper.PriceCouponConfigMapper;
import com.ycwl.basic.repository.ScenicRepository;
import com.ycwl.basic.service.notify.WechatSubscribeNotifyTriggerService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Profile;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

import java.util.Date;
import java.util.HashMap;
import java.util.List;

@Component
@EnableScheduling
@Slf4j
@Profile("prod")
public class CouponExpireNotificationTask {

    @Autowired
    private PriceCouponClaimRecordMapper couponClaimRecordMapper;

    @Autowired
    private MemberMapper memberMapper;

    @Autowired
    private WechatSubscribeNotifyTriggerService notifyTriggerService;
    @Autowired
    private PriceCouponConfigMapper priceCouponConfigMapper;
    @Autowired
    private ScenicRepository scenicRepository;

    @Scheduled(cron = "0 0 20 * * *")
    public void sendCouponExpireNotification() {
        log.info("开始执行优惠券过期提醒定时任务");
        processNotification("COUPON_EXPIRE", -2);
        log.info("优惠券过期提醒定时任务执行结束");
    }

    @Scheduled(cron = "0 0 8 * * *")
    public void sendCouponPreExpireNotification() {
        log.info("开始执行优惠券临期提醒定时任务");
        processNotification("COUPON_PRE_EXPIRE", -2);
        log.info("优惠券临期提醒定时任务执行结束");
    }

    @Scheduled(cron = "0 30 10-22 * * *")
    public void sendCouponReceivedNotification() {
        log.info("开始执行优惠券领取通知定时任务");
        Date now = new Date();
        Date beginTime = DateUtil.offsetHour(now, -3);
        Date endTime = DateUtil.offsetHour(now, -2);

        log.info("查询时间范围: {} - {}", beginTime, endTime);

        LambdaQueryWrapper<PriceCouponClaimRecord> queryWrapper = Wrappers.lambdaQuery();
        queryWrapper.between(PriceCouponClaimRecord::getCreateTime, beginTime, endTime);
        queryWrapper.eq(PriceCouponClaimRecord::getStatus, CouponStatus.CLAIMED);

        List<PriceCouponClaimRecord> couponRecords = couponClaimRecordMapper.selectList(queryWrapper);
        processRecords(couponRecords, "COUPON_NOTICE");
        log.info("优惠券领取通知定时任务执行结束");
    }

    @Scheduled(cron = "0 0 18 * * *")
    public void sendCouponPastHalfNotification() {
        log.info("开始执行优惠券有效期过半提醒定时任务");
        processNotification("COUPON_PAST_HALF", -1);
        log.info("优惠券有效期过半提醒定时任务执行结束");
    }

    private void processNotification(String notifyType, int offsetDays) {
        // 获取指定偏移天数（例如-2 days）的开始和结束时间
        Date date = DateUtil.offsetDay(new Date(), offsetDays);
        Date beginTime = DateUtil.beginOfDay(date);
        Date endTime = DateUtil.endOfDay(date);

        log.info("查询时间范围: {} - {}", beginTime, endTime);

        // 查询该时间段内创建的优惠券记录
        LambdaQueryWrapper<PriceCouponClaimRecord> queryWrapper = Wrappers.lambdaQuery();
        queryWrapper.between(PriceCouponClaimRecord::getCreateTime, beginTime, endTime);
        queryWrapper.eq(PriceCouponClaimRecord::getStatus, CouponStatus.CLAIMED);

        List<PriceCouponClaimRecord> couponRecords = couponClaimRecordMapper.selectList(queryWrapper);
        processRecords(couponRecords, notifyType);
    }

    private void processRecords(List<PriceCouponClaimRecord> couponRecords, String notifyType) {
        if (couponRecords == null || couponRecords.isEmpty()) {
            log.info("未找到符合条件的优惠券记录");
            return;
        }

        log.info("找到 {} 条优惠券记录", couponRecords.size());

        for (PriceCouponClaimRecord record : couponRecords) {
            try {
                MemberRespVO member = memberMapper.getById(record.getUserId());
                if (member == null || member.getOpenId() == null) {
                    continue;
                }
                ScenicV2DTO scenicBasic = scenicRepository.getScenicBasic(member.getScenicId());
                PriceCouponConfig coupon = priceCouponConfigMapper.selectValidCouponById(record.getCouponId());

                HashMap<String, Object> variables = new HashMap<>();
                variables.put("couponName", coupon.getCouponName());
                variables.put("couponValue", coupon.getDiscountValue());
                variables.put("couponType", coupon.getCouponType().getDescription());
                // 优惠券有效期到第二天的结束，从领取开始的时候算
                variables.put("couponStartTime", DateUtil.format(record.getCreateTime(), "yyyy-MM-dd HH:mm"));
                variables.put("couponExpireTime", DateUtil.format(DateUtil.endOfDay(DateUtil.offsetDay(record.getCreateTime(), 2)), "yyyy-MM-dd HH:mm"));
                variables.put("scenicId", member.getScenicId());
                variables.put("scenicName", scenicBasic.getName());

                WechatSubscribeNotifyTriggerRequest request = WechatSubscribeNotifyTriggerRequest.builder()
                        .scenicId(member.getScenicId())
                        .memberId(record.getUserId())
                        .openId(member.getOpenId())
                        .bizId(String.valueOf(record.getId()))
                        .variables(variables)
                        .build();

                // 触发消息
                notifyTriggerService.trigger(notifyType, request);

            } catch (Exception e) {
                log.error("发送通知失败, type: {}, recordId: {}", notifyType, record.getId(), e);
            }
        }
    }
}
