package com.fs.course.service.impl;

import java.math.BigDecimal;
import java.math.BigInteger;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.function.Function;
import java.util.stream.Collectors;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.fs.common.core.domain.R;
import com.fs.common.utils.DateUtils;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.fs.common.utils.date.DateUtil;
import com.fs.common.utils.date.TimeTypeEnum;
import com.fs.course.domain.FsUserCoursePeriod;
import com.fs.course.mapper.FsUserCoursePeriodMapper;
import com.fs.course.param.CompanyRedPacketParam;
import com.fs.course.param.PeriodCountParam;
import com.fs.course.param.PeriodRedPacketParam;
import com.fs.course.vo.FsPeriodCountVO;
import com.fs.course.vo.newfs.FsCourseAnalysisCountVO;
import com.fs.store.mapper.FsUserMapper;
import com.fs.store.param.h5.CourseAnalysisParam;
import lombok.AllArgsConstructor;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import com.fs.course.mapper.FsUserCoursePeriodDaysMapper;
import com.fs.course.domain.FsUserCoursePeriodDays;
import com.fs.course.service.IFsUserCoursePeriodDaysService;

/**
 * 营期课程Service业务层处理
 *
 * @author fs
 * @date 2025-04-16
 */
@Service
@AllArgsConstructor
public class FsUserCoursePeriodDaysServiceImpl extends ServiceImpl<FsUserCoursePeriodDaysMapper, FsUserCoursePeriodDays> implements IFsUserCoursePeriodDaysService {

    private final FsUserCoursePeriodMapper fsUserCoursePeriodMapper;

    private final FsUserMapper  fsUserMapper;

    /**
     * 查询营期课程
     *
     * @param id 营期课程主键
     * @return 营期课程
     */
    @Override
    public FsUserCoursePeriodDays selectFsUserCoursePeriodDaysById(Long id)
    {
        return baseMapper.selectFsUserCoursePeriodDaysById(id);
    }

    /**
     * 查询营期课程列表
     *
     * @param fsUserCoursePeriodDays 营期课程
     * @return 营期课程
     */
    @Override
    public List<FsUserCoursePeriodDays> selectFsUserCoursePeriodDaysList(FsUserCoursePeriodDays fsUserCoursePeriodDays)
    {
        return baseMapper.selectFsUserCoursePeriodDaysList(fsUserCoursePeriodDays);
    }

    /**
     * 新增营期课程
     *
     * @param fsUserCoursePeriodDays 营期课程
     * @return 结果
     */
    @Override
    public int insertFsUserCoursePeriodDays(FsUserCoursePeriodDays fsUserCoursePeriodDays)
    {
        fsUserCoursePeriodDays.setCreateTime(DateUtils.getNowDate());
        return baseMapper.insert(fsUserCoursePeriodDays);
    }

    /**
     * 修改营期课程
     *
     * @param fsUserCoursePeriodDays 营期课程
     * @return 结果
     */
    @Override
    public int updateFsUserCoursePeriodDays(FsUserCoursePeriodDays fsUserCoursePeriodDays)
    {
        fsUserCoursePeriodDays.setUpdateTime(DateUtils.getNowDate());
        return baseMapper.updateById(fsUserCoursePeriodDays);
    }

    /**
     * 批量删除营期课程
     *
     * @param ids 需要删除的营期课程主键
     * @return 结果
     */
    @Override
    public int deleteFsUserCoursePeriodDaysByIds(Long[] ids)
    {
        return baseMapper.deleteFsUserCoursePeriodDaysByIds(ids);
    }

    /**
     * 删除营期课程信息
     *
     * @param id 营期课程主键
     * @return 结果
     */
    @Override
    public int deleteFsUserCoursePeriodDaysById(Long id)
    {
        return baseMapper.deleteFsUserCoursePeriodDaysById(id);
    }

    @Override
    public R addCourse(FsUserCoursePeriodDays entity) {
        FsUserCoursePeriod period = fsUserCoursePeriodMapper.selectFsUserCoursePeriodById(entity.getPeriodId());
        int num = count(new QueryWrapper<FsUserCoursePeriodDays>().eq("period_id", period.getPeriodId()));
        long days;
        if(period.getPeriodType() == 2){
            days = 1;
        }else{
            days = DateUtil.differenceTime(period.getPeriodStartingTime(), period.getPeriodEndTime(), TimeTypeEnum.DAY);
        }
        days++;
        if(num + entity.getVideoIds().size() > days) return R.error("课程不能超过营期范围");
        AtomicInteger i = new AtomicInteger(0);
        List<FsUserCoursePeriodDays> collect = entity.getVideoIds().stream().map(e -> {
            FsUserCoursePeriodDays day = new FsUserCoursePeriodDays();
            day.setPeriodId(entity.getPeriodId());
            day.setLesson(num + i.getAndIncrement());
            day.setDayDate(period.getPeriodStartingTime().plusDays(day.getLesson()));
            day.setCourseId(entity.getCourseId());
            day.setVideoId(e);
            day.setCreateTime(new Date());
            return day;
        }).collect(Collectors.toList());
        super.saveBatch(collect);
        return R.ok();
    }

    @Override
    public R updateListCourseData(List<FsUserCoursePeriodDays> entity) {
        List<FsUserCoursePeriodDays> collect = entity.stream().map(e -> {
            FsUserCoursePeriodDays day = new FsUserCoursePeriodDays();
            day.setId(e.getId());
            day.setMoney(e.getMoney());
            return day;
        }).collect(Collectors.toList());
        super.updateBatchById(collect);
        return R.ok();
    }

    @Override
    public List<CompanyRedPacketParam> getCompanyByPeriod(Long periodId, Long videoId) {
        if(videoId == null ){
            return fsUserCoursePeriodMapper.selectCompanyByPeriod(periodId);
        }
        return fsUserCoursePeriodMapper.selectCompanyByPeriodVideo(periodId, videoId);
    }

    @Override
    public List<PeriodRedPacketParam> getPeriodRedPacketList(Long periodId, Long companyId) {
        return fsUserCoursePeriodMapper.selectPeriodRedPacket(periodId, companyId);
    }

    @Override
    public List<FsPeriodCountVO> periodCourseCount(PeriodCountParam param) {
        //1、查询课程视频信息
        FsUserCoursePeriodDays fsUserCoursePeriodDays = new FsUserCoursePeriodDays();
        fsUserCoursePeriodDays.setPeriodId(param.getPeriodId());
        fsUserCoursePeriodDays.setVideoIds(param.getVideoIdList());

        List<FsUserCoursePeriodDays> videoList = baseMapper.selectFsUserCoursePeriodDaysList(fsUserCoursePeriodDays);

        //2、查询统计
        CourseAnalysisParam courseAnalysisParam = new CourseAnalysisParam();
        courseAnalysisParam.setPeriodId(param.getPeriodId());
        courseAnalysisParam.setVideoIdList(param.getVideoIdList());
        List<FsCourseAnalysisCountVO> courseCountList = fsUserMapper.courseAnalysisWatchLog(courseAnalysisParam);
        List<FsCourseAnalysisCountVO> redPacketCountList = fsUserMapper.courseAnalysisRedPacketCount(courseAnalysisParam);
        List<FsCourseAnalysisCountVO> answerCountList = fsUserMapper.courseAnalysisAnswerCount(courseAnalysisParam);

        //3、转化为map
        Map<Long, FsCourseAnalysisCountVO> courseMap = courseCountList.stream()
                .collect(Collectors.toMap(
                        FsCourseAnalysisCountVO::getVideoId,
                        Function.identity()
                ));
        Map<Long, FsCourseAnalysisCountVO> redPacketMap = redPacketCountList.stream()
                .collect(Collectors.toMap(
                        FsCourseAnalysisCountVO::getVideoId,
                        Function.identity()
                ));
        Map<Long, FsCourseAnalysisCountVO> answerMap = answerCountList.stream()
                .collect(Collectors.toMap(
                        FsCourseAnalysisCountVO::getVideoId,
                        Function.identity()
                ));

        //4、处理数据
        return videoList.stream().map(v -> {
            FsPeriodCountVO allVO = new FsPeriodCountVO();
            BeanUtils.copyProperties(v, allVO);
            allVO.setTitle(v.getVideoName());

            FsCourseAnalysisCountVO countVO = getCourseAnalysisCountVO(v, courseMap, redPacketMap, answerMap);
            allVO.setCountDetailsVO(countVO);
            return allVO;
        }).collect(Collectors.toList());
    }

    private static FsCourseAnalysisCountVO getCourseAnalysisCountVO(FsUserCoursePeriodDays v, Map<Long, FsCourseAnalysisCountVO> courseMap, Map<Long, FsCourseAnalysisCountVO> redPacketMap, Map<Long, FsCourseAnalysisCountVO> answerMap) {
        FsCourseAnalysisCountVO countVO = new FsCourseAnalysisCountVO();
        FsCourseAnalysisCountVO courseVO = courseMap.getOrDefault(v.getVideoId(), countVO);
        FsCourseAnalysisCountVO redPacketVO = redPacketMap.getOrDefault(v.getVideoId(), countVO);
        FsCourseAnalysisCountVO answerVO = answerMap.getOrDefault(v.getVideoId(), countVO);
        //单独赋值
        countVO.setVideoId(v.getVideoId()).setCourseWatchNum(courseVO.getCourseWatchNum()).setCourseCompleteNum(courseVO.getCourseWatchNum())
                .setCompleteRate(courseVO.getCompleteRate() != null ? courseVO.getCompleteRate() : new BigDecimal(BigInteger.ZERO))
                .setCourseWatchTimes(courseVO.getCourseWatchTimes()).setCourseCompleteTimes(courseVO.getCourseCompleteTimes());
        countVO.setRedPacketNum(redPacketVO.getRedPacketNum())
                .setRedPacketAmount(redPacketVO.getRedPacketAmount() != null ? redPacketVO.getRedPacketAmount() : new BigDecimal(BigInteger.ZERO));
        countVO.setAnswerNum(answerVO.getAnswerNum()).setAnswerRightNum(answerVO.getAnswerRightNum())
                .setAnswerRightRate(answerVO.getAnswerRightRate()!=null ? answerVO.getAnswerRightRate() : new BigDecimal(BigInteger.ZERO))
                .setAnswerTimes(answerVO.getAnswerTimes()).setAnswerRightTimes(answerVO.getAnswerRightTimes());
        return countVO;
    }
}
