package com.kym.admin.jobs;

import cn.hutool.core.date.DateUtil;
import com.kym.entity.DailyStat;
import com.kym.entity.MonthStat;
import com.kym.service.*;
import lombok.extern.slf4j.Slf4j;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;

/**
 * 数据统计定时任务
 */
@Component
@Slf4j
public class StatJob {

    private final UserService userService;

    private final WashOrderService washOrderService;

    private final DailyStatService dailyStatService;

    private final MonthStatService monthStatService;

    private final SplitRecordService splitRecordService;

    public StatJob(UserService userService, WashOrderService washOrderService, DailyStatService dailyStatService, MonthStatService monthStatService, SplitRecordService splitRecordService) {
        this.userService = userService;
        this.washOrderService = washOrderService;
        this.dailyStatService = dailyStatService;
        this.monthStatService = monthStatService;
        this.splitRecordService = splitRecordService;
    }

    /**
     * 统计前一天的消费金额，注册人数，订单数量
     * 每天凌晨00:30执行一次
     */
    @Scheduled(cron = "0 30 0 * * ?")
    public void generateDailyStat() {
        log.info("执行站点日统计定时任务-开始");
        LocalDate yesterday = LocalDate.now().minusDays(1);

        // 各站点总订单金额，注册会员人数，订单数量
        var amountMap = washOrderService.sumAmountByDate(yesterday);
        var registerMap = userService.countDailyRegister(yesterday);
        var ordersCountMap = washOrderService.countDailyOrders(yesterday);

        // 各站点总收入
        var incomeMap = splitRecordService.sumDailyIncome(yesterday);
        // 各站点跨店收入
        var crossIncomeMap = splitRecordService.sumDailyIncome(yesterday, Boolean.TRUE);
        // 各站点跨店支出
        var expendMap = splitRecordService.sumDailyExpend(yesterday);

        var statList = new ArrayList<DailyStat>();
        amountMap.forEach((k, v) -> {
            DailyStat stat = new DailyStat();
            stat.setStatDate(DateUtil.format(LocalDateTime.now().minusDays(1), "yyyy-MM-dd"));
            stat.setStationId(k);
            stat.setConsumption(v);
            stat.setRegistrations(registerMap.getOrDefault(k, 0));
            stat.setOrdersCount(ordersCountMap.getOrDefault(k, 0));
            stat.setTotalIncome(incomeMap.getOrDefault(k, 0));
            stat.setCrossIncome(crossIncomeMap.getOrDefault(k, 0));
            stat.setCrossExpend(expendMap.getOrDefault(k, 0));
            statList.add(stat);
        });
        dailyStatService.replaceBatch(statList);
        log.info("执行站点日统计定时任务-结束");
    }


    /**
     * 月统计，每月5日天下午15:00启动，统计上月数据
     */
    @Scheduled(cron = "0 0 15 5 * ?")
    private void generateMonthStat() {
        log.info("执行站点月统计定时任务-开始");
        var statMonth = LocalDate.now().minusMonths(1);
        var amountMap = washOrderService.sumMonthAmount(statMonth);
        var registerMap = userService.countMonthRegister(statMonth);
        var ordersCountMap = washOrderService.countMonthOrders(statMonth);

        // 各站点总收入
        var incomeMap = splitRecordService.sumMonthIncome(statMonth);
        // 各站点跨店收入
        var crossIncomeMap = splitRecordService.sumMonthIncome(statMonth, Boolean.TRUE);
        // 各站点跨店支出
        var expendMap = splitRecordService.sumMonthExpend(statMonth);

        var statList = new ArrayList<MonthStat>();
        amountMap.forEach((k, v) -> {
            MonthStat stat = new MonthStat();
            stat.setStatMonth(DateUtil.format(LocalDateTime.now().minusMonths(1), "yyyy-MM"));
            stat.setStationId(k);
            stat.setConsumption(v);
            stat.setRegistrations(registerMap.getOrDefault(k, 0));
            stat.setOrdersCount(ordersCountMap.getOrDefault(k, 0));
            stat.setTotalIncome(incomeMap.getOrDefault(k, 0));
            stat.setCrossIncome(crossIncomeMap.getOrDefault(k, 0));
            stat.setCrossExpend(expendMap.getOrDefault(k, 0));
            statList.add(stat);
        });
        monthStatService.replaceBatch(statList);
        log.info("执行站点月统计定时任务-结束");
    }

}
