package com.izouma.dingdong.service;

import com.izouma.dingdong.domain.PlatformFlow;
import com.izouma.dingdong.domain.User;
import com.izouma.dingdong.enums.ApplyStatus;
import com.izouma.dingdong.enums.FlowType;
import com.izouma.dingdong.enums.Identity;
import com.izouma.dingdong.enums.OrderStatus;
import com.izouma.dingdong.repo.OrderInfoRepo;
import com.izouma.dingdong.repo.PlatformFlowRepo;
import com.izouma.dingdong.repo.UserRepo;
import com.izouma.dingdong.repo.merchant.MerchantRepo;
import com.izouma.dingdong.repo.rider.RiderRepo;
import lombok.AllArgsConstructor;
import org.springframework.stereotype.Service;

import java.math.BigDecimal;
import java.text.SimpleDateFormat;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.format.DateTimeFormatter;
import java.time.temporal.TemporalAdjusters;
import java.util.*;

@Service
@AllArgsConstructor
public class PlatformFlowService {

    private PlatformFlowRepo platformFlowRepo;
    private UserRepo         userRepo;
    private MerchantRepo     merchantRepo;
    private RiderRepo        riderRepo;
    private OrderInfoRepo    orderInfoRepo;

    /*
    报表
     */
    public Map<String, Object> getDashboard() {
        Map<String, Object> map = new HashMap<>();
        Long user = userRepo.countAllByIdentity(Identity.USER);
        Long merchant = merchantRepo.countAllByStatus(ApplyStatus.PASS);
        Long rider = riderRepo.countAllByStatus(ApplyStatus.PASS);
        Long order = orderInfoRepo.count();
        map.put("user", user);
        map.put("merchant", merchant);
        map.put("rider", rider);
        map.put("order", order);
        return map;
    }


    public Map<Object, BigDecimal> statistics(String type, FlowType flowType) {
        if (type.equals("DATE")) {
            return dayStatistics(flowType);
        }
        return getVipSummary(flowType);
    }

    /*
   7天内的金钱统计
    */
    public Map<Object, BigDecimal> dayStatistics(FlowType type) {
        Map<Object, BigDecimal> statistics = new HashMap<>(7);
        LocalDateTime today = LocalDateTime.now();
        LocalDateTime last = LocalDateTime.of(today.toLocalDate(), LocalTime.MIN);

        int i = 7;
        while (i > 0) {
            BigDecimal add = platformFlowRepo.findAllByTypeAndTimeBetween(type, last, today)
                    .stream()
                    .map(PlatformFlow::getAmount)
                    .reduce(BigDecimal::add)
                    .orElse(BigDecimal.ZERO);
            statistics.put(today.toLocalDate(), add);
            i--;
            today = last;
            last = today.minusDays(1);
        }
        return statistics;
    }

    /*
    半年内的金钱统计
     */
    public BigDecimal monthAmount(Integer month, FlowType type) {

        //计算该月份的第一天
        Calendar calendar = Calendar.getInstance();
        // 设置月份
        calendar.set(Calendar.MONTH, month - 1);
        // 获取某月最小天数
        int firstDay = calendar.getActualMinimum(Calendar.DAY_OF_MONTH);
        // 设置日历中月份的最小天数
        calendar.set(Calendar.DAY_OF_MONTH, firstDay);
        // 格式化日期
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
        DateTimeFormatter df = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
        LocalDateTime start = LocalDateTime.parse(sdf.format(calendar.getTime()) + " 00:00:00", df);

        // 计算当前月份的最后一天
        Calendar calendar2 = Calendar.getInstance();
        // 设置月份
        calendar2.set(Calendar.MONTH, month - 1);
        // 获取某月最大天数
        int lastDay = calendar2.getActualMaximum(Calendar.DAY_OF_MONTH);
        // 设置日历中月份的最大天数
        calendar2.set(Calendar.DAY_OF_MONTH, lastDay);
        LocalDateTime end = LocalDateTime.parse(sdf.format(calendar2.getTime()) + " 23:59:59", df);

        // false线下会员，true线上
        return platformFlowRepo.findAllByTypeAndTimeBetween(type, start, end)
                .stream()
                .map(PlatformFlow::getAmount)
                .reduce(BigDecimal::add)
                .orElse(BigDecimal.ZERO);


    }

    /*
    每个顺序
     */
    public Map<Object, BigDecimal> getVipSummary(FlowType type) {
        int nowMonth = LocalDateTime.now().getMonthValue();
        List<Integer> monthList = new ArrayList<Integer>();
        int monthScape = 6;
        for (int i = 0; i <= monthScape; i++) {
            if (i != 0) {
                if (nowMonth != 1) {
                    nowMonth = nowMonth - 1;
                } else {
                    break;
                }

            }
            monthList.add(nowMonth);
        }
        Map<Object, BigDecimal> monthNewInMap = new HashMap<>(7);
        monthList.forEach(month ->
                monthNewInMap.put(month, monthAmount(month, type))
        );
        return monthNewInMap;
    }

//    public Map<String, Long> getHotSaleGoods(String type) {
//        LocalDate today = LocalDate.now();
//        switch (type) {
//            case "DATE":
//                return countDayMostSaleGoods();
//            case "WEEK":
//                LocalDate weekStart = today.minusDays(6);
//                List<GoodsSale> goodsSales = orderFormGoodRepo.countAllByCreatedAtBetween(weekStart.atStartOfDay(), today.atTime(23, 59, 59, 99));
//                Map<String, Long> goodsSaleCounts = new HashMap<>();
//                goodsSales.forEach(goodsSale -> {
//                    String goodName = goodsRepo.findById(goodsSale.getGoodsId()).orElse(Goods.builder().name("数据已丢失").build()).getName();
//                    goodsSaleCounts.put(goodName, goodsSale.getSales());
//                });
//                return goodsSaleCounts;
//            case "MONTH":
//                LocalDate monthStart = today.with(TemporalAdjusters.firstDayOfMonth());
//                LocalDate monthEnd = today.with(TemporalAdjusters.lastDayOfMonth());
//                Map<String, Long> goodsSaleCounts2 = new HashMap<>();
//                List<GoodsSale> goodsSales1 = orderFormGoodRepo.countAllByCreatedAtBetween(monthStart.atStartOfDay(), monthEnd.atTime(23, 59, 59, 99));
//                goodsSales1.forEach(goodsSale -> {
//                    String goodName = goodsRepo.findById(goodsSale.getGoodsId()).orElse(Goods.builder().name("数据已丢失").build()).getName();
//                    goodsSaleCounts2.put(goodName, goodsSale.getSales());
//                });
//                return goodsSaleCounts2;
//            default:
//                return null;
//        }
//    }

}
