package com.ym.mec.biz.service.impl;

import java.math.BigDecimal;
import java.util.Date;
import java.util.List;
import java.util.Set;
import java.util.stream.Collectors;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.ym.mec.biz.dal.dao.CloudTeacherDao;
import com.ym.mec.biz.dal.dao.CloudTeacherOrderDao;
import com.ym.mec.biz.dal.dao.CourseScheduleDao;
import com.ym.mec.biz.dal.dao.StudentPaymentOrderDetailDao;
import com.ym.mec.biz.dal.dto.CloudTeacherOrderDto;
import com.ym.mec.biz.dal.entity.CloudTeacher;
import com.ym.mec.biz.dal.entity.CloudTeacherOrder;
import com.ym.mec.biz.dal.entity.CourseSchedule;
import com.ym.mec.biz.dal.entity.StudentPaymentOrder;
import com.ym.mec.biz.dal.enums.PeriodEnum;
import com.ym.mec.biz.service.CloudTeacherOrderService;
import com.ym.mec.biz.service.StudentService;
import com.ym.mec.common.dal.BaseDAO;
import com.ym.mec.common.exception.BizException;
import com.ym.mec.common.service.impl.BaseServiceImpl;
import com.ym.mec.util.date.DateUtil;

@Service
public class CloudTeacherOrderServiceImpl extends BaseServiceImpl<Long, CloudTeacherOrder> implements CloudTeacherOrderService {

    @Autowired
    private CloudTeacherOrderDao cloudTeacherOrderDao;
    @Autowired
    private StudentPaymentOrderDetailDao studentPaymentOrderDetailDao;
    @Autowired
    private CourseScheduleDao courseScheduleDao;
    @Autowired
    private CloudTeacherDao cloudTeacherDao;
    
    @Autowired
    private StudentService studentService;


    @Override
    public BaseDAO<Long, CloudTeacherOrder> getDAO() {
        return cloudTeacherOrderDao;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
	public Boolean addOrderDetail2CloudTeacher(StudentPaymentOrder order) {
		CloudTeacherOrder cloudTeacherOrder = cloudTeacherOrderDao.queryByOrderId(order.getId());

		if (cloudTeacherOrder == null) {
			return true;
		}
		Date date = new Date();

		cloudTeacherOrder.setStatus(1);
		cloudTeacherOrder.setUpdateTime(date);

		cloudTeacherOrderDao.update(cloudTeacherOrder);

		return true;
	}

    @Override
    public Boolean checkCloudOrderStart() {
        List<CloudTeacherOrder> cloudTeacherOrders = cloudTeacherOrderDao.getNoStartCloudTeacherOrder();
        List<String> musicGroupIds = cloudTeacherOrders.stream().map(CloudTeacherOrder::getMusicGroupId).collect(Collectors.toList());
        List<CourseSchedule> musicGroupsHasStartCourseNum = courseScheduleDao.getMusicGroupsHasStartCourseNum(musicGroupIds);
        Set<String> musicGroupHasStartCourse = musicGroupsHasStartCourseNum.stream().map(CourseSchedule::getMusicGroupId).collect(Collectors.toSet());
        for (CloudTeacherOrder cloudTeacherOrder : cloudTeacherOrders) {
            if (!musicGroupHasStartCourse.contains(cloudTeacherOrder.getMusicGroupId())) continue;
            addStudentCloudTeacher(cloudTeacherOrder);
        }
        return true;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public CloudTeacher addStudentCloudTeacher(CloudTeacherOrder cloudTeacherOrder) {
        Date nowDate = new Date();
        CloudTeacher cloudTeacher = cloudTeacherDao.getByStudentId(cloudTeacherOrder.getStudentId());
        Date startTime = null;
        Date endTime = null;
        Date endBaseTime = null;
        
        PeriodEnum periodEnum = PeriodEnum.MONTH;
		switch (cloudTeacherOrder.getType()) {
		case 1:
			periodEnum = PeriodEnum.DAY;
			break;
		case 2:
			periodEnum = PeriodEnum.MONTH;
			break;
		case 3:
			periodEnum = PeriodEnum.YEAR;
			break;

		default:
			break;
		}
        //更新student表信息
        studentService.updateMemberRank(cloudTeacherOrder.getStudentId(), cloudTeacherOrder.getLevel(), periodEnum, cloudTeacherOrder.getTime());
        
        if (cloudTeacher == null) {
            cloudTeacher = new CloudTeacher();
            startTime = DateUtil.trunc(nowDate);
            endBaseTime = startTime;
            if (cloudTeacherOrder.getType().equals(1)) {
                endTime = DateUtil.addDays(startTime, cloudTeacherOrder.getTime());
            } else if (cloudTeacherOrder.getType().equals(2)) {
                endTime = DateUtil.addMonths(startTime, cloudTeacherOrder.getTime());
            } else if (cloudTeacherOrder.getType().equals(3)) {
                endTime = DateUtil.addYears(startTime, cloudTeacherOrder.getTime());
            }
            cloudTeacher.setStudentId(cloudTeacherOrder.getStudentId());
            cloudTeacher.setLevel(cloudTeacherOrder.getLevel());
            cloudTeacher.setStartTime(startTime);
            cloudTeacher.setEndTime(endTime);
            cloudTeacherDao.insert(cloudTeacher);
        } else {
            startTime = cloudTeacher.getStartTime();
            endBaseTime = cloudTeacher.getEndTime();
            if (cloudTeacher.getEndTime().compareTo(nowDate) < 0) {
                startTime = DateUtil.trunc(nowDate);
                endBaseTime = startTime;
            }
            if (cloudTeacherOrder.getType().equals(1)) {
                endTime = DateUtil.addDays(endBaseTime, cloudTeacherOrder.getTime());
            } else if (cloudTeacherOrder.getType().equals(2)) {
                endTime = DateUtil.addMonths(endBaseTime, cloudTeacherOrder.getTime());
            } else if (cloudTeacherOrder.getType().equals(3)) {
                endTime = DateUtil.addYears(endBaseTime, cloudTeacherOrder.getTime());
            }
            cloudTeacher.setStartTime(startTime);
            cloudTeacher.setEndTime(endTime);
            cloudTeacher.setUpdateTime(nowDate);
            if (cloudTeacherDao.update(cloudTeacher) <= 0) {
                throw new BizException("云教练有效期更新失败");
            }
        }
        cloudTeacherOrder.setStartTime(endBaseTime);
        cloudTeacherOrder.setEndTime(endTime);
        cloudTeacherOrder.setStatus(2);
        if (cloudTeacherOrderDao.update(cloudTeacherOrder) <= 0) {
            throw new BizException("云教练生效处理失败");
        }
        return cloudTeacher;
    }

    @Override
    public List<CloudTeacherOrder> getStudentCloudTeacherOrders(List<Integer> studentIds, String musicGroupId) {
        return cloudTeacherOrderDao.getStudentCloudTeacherOrders(studentIds, musicGroupId);
    }

    @Override
    public List<CloudTeacherOrder> getStudentCloudTeacherOrder(Integer studentId, String musicGroupId) {
        return cloudTeacherOrderDao.getStudentCloudTeacherOrder(studentId, musicGroupId);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean quitCloudTeacherOrders(List<CloudTeacherOrder> cloudTeacherOrders, BigDecimal refundAmount) {
        Date nowDate = new Date();
        for (int i = 0; i < cloudTeacherOrders.size(); i++) {
            CloudTeacherOrder cloudTeacherOrder = cloudTeacherOrders.get(i);
            if (cloudTeacherOrder.getStatus().equals(3)) {
                throw new BizException("云教练已退，请勿重复退");
            }
            if (cloudTeacherOrder.getStatus().equals(2) && DateUtil.stringToDate(DateUtil.format(cloudTeacherOrder.getEndTime(),DateUtil.ISO_EXPANDED_DATE_FORMAT),DateUtil.ISO_EXPANDED_DATE_FORMAT).compareTo(
                    DateUtil.stringToDate(DateUtil.format(nowDate,DateUtil.ISO_EXPANDED_DATE_FORMAT),DateUtil.ISO_EXPANDED_DATE_FORMAT)) < 0) {
                throw new BizException("云教练已过服务期，不可退费");
            }
            Integer oldStatus = cloudTeacherOrder.getStatus();
            cloudTeacherOrder.setStatus(3);
            if(i == 0){
                cloudTeacherOrder.setRefundAmount(refundAmount);
            }else {
                cloudTeacherOrder.setRefundAmount(BigDecimal.ZERO);
            }
            cloudTeacherOrder.setUpdateTime(nowDate);
            if (cloudTeacherOrderDao.update(cloudTeacherOrder) <= 0) {
                throw new BizException("云教练退费处理失败，请重试");
            }

            if (oldStatus.equals(1)) {
                return true;
            }
            int days = DateUtil.daysBetween(DateUtil.trunc(nowDate), cloudTeacherOrder.getEndTime());
            CloudTeacher cloudTeacher = cloudTeacherDao.getByStudentId(cloudTeacherOrder.getStudentId());
            Date endDate = DateUtil.addDays(cloudTeacherOrder.getEndTime(), -days);
            cloudTeacher.setEndTime(endDate);
            cloudTeacher.setUpdateTime(nowDate);
            if (cloudTeacherDao.update(cloudTeacher) <= 0) {
                throw new BizException("云教练服务有效期更新失败，请重试");
            }
        }
        return true;
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Boolean quitCloudTeacherOrder(CloudTeacherOrder cloudOrder, BigDecimal refundAmount) {
        Date nowDate = new Date();
        if (cloudOrder.getStatus().equals(3)) {
            throw new BizException("云教练已退，请勿重复退");
        }
        if (cloudOrder.getStatus().equals(2) && DateUtil.stringToDate(DateUtil.format(cloudOrder.getEndTime(),DateUtil.ISO_EXPANDED_DATE_FORMAT),DateUtil.ISO_EXPANDED_DATE_FORMAT).compareTo(
                DateUtil.stringToDate(DateUtil.format(nowDate,DateUtil.ISO_EXPANDED_DATE_FORMAT),DateUtil.ISO_EXPANDED_DATE_FORMAT)) < 0) {
            throw new BizException("云教练已过服务期，不可退费");
        }
        Integer oldStatus = cloudOrder.getStatus();
        cloudOrder.setStatus(3);
        cloudOrder.setRefundAmount(refundAmount);
        cloudOrder.setUpdateTime(nowDate);
        if (cloudTeacherOrderDao.update(cloudOrder) <= 0) {
            throw new BizException("云教练退费处理失败，请重试");
        }

        if (oldStatus.equals(1)) {
            return true;
        }
        int days = DateUtil.daysBetween(DateUtil.trunc(nowDate), cloudOrder.getEndTime());
        CloudTeacher cloudTeacher = cloudTeacherDao.getByStudentId(cloudOrder.getStudentId());
        Date endDate = DateUtil.addDays(cloudOrder.getEndTime(), -days);
        cloudTeacher.setEndTime(endDate);
        cloudTeacher.setUpdateTime(nowDate);
        if (cloudTeacherDao.update(cloudTeacher) <= 0) {
            throw new BizException("云教练服务有效期更新失败，请重试");
        }
        return true;
    }

	@Override
	public CloudTeacherOrder queryByOrderId(Long orderId) {
		return cloudTeacherOrderDao.queryByOrderId(orderId);
	}

	@Override
	public CloudTeacherOrderDto queryOrderInfoByOrderId(Long orderId) {
		return cloudTeacherOrderDao.queryOrderInfoByOrderId(orderId);
	}
}
