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

import com.ym.mec.biz.dal.dao.CourseHomeworkDao;
import com.ym.mec.biz.dal.dao.CourseScheduleDao;
import com.ym.mec.biz.dal.dao.StudentCourseHomeworkDao;
import com.ym.mec.biz.dal.dao.StudentCourseHomeworkReplyDao;
import com.ym.mec.biz.dal.dto.Mapper;
import com.ym.mec.biz.dal.dto.TeacherHomeworkListDto;
import com.ym.mec.biz.dal.dto.WebCourseHomeworkListDto;
import com.ym.mec.biz.dal.entity.CourseHomework;
import com.ym.mec.biz.dal.entity.CourseSchedule;
import com.ym.mec.biz.dal.entity.StudentCourseHomework;
import com.ym.mec.biz.dal.enums.MessageTypeEnum;
import com.ym.mec.biz.dal.enums.YesOrNoEnum;
import com.ym.mec.biz.dal.page.CourseHomeWorkTemplateQueryInfo;
import com.ym.mec.biz.dal.page.CourseHomeworkQueryInfo;
import com.ym.mec.biz.service.CourseHomeworkService;
import com.ym.mec.biz.service.SysMessageService;
import com.ym.mec.common.dal.BaseDAO;
import com.ym.mec.common.exception.BizException;
import com.ym.mec.common.page.PageInfo;
import com.ym.mec.common.service.impl.BaseServiceImpl;
import com.ym.mec.thirdparty.message.MessageSenderPluginContext.MessageSender;
import com.ym.mec.util.collection.MapUtil;
import com.ym.mec.util.date.DateUtil;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.util.*;
import java.util.stream.Collectors;

@Service
public class CourseHomeworkServiceImpl extends BaseServiceImpl<Long, CourseHomework> implements CourseHomeworkService {

	@Autowired
	private CourseHomeworkDao courseHomeworkDao;

	@Autowired
	private StudentCourseHomeworkDao studentCourseHomeworkDao;

	@Autowired
	private StudentCourseHomeworkReplyDao studentCourseHomeworkReplyDao;

	@Autowired
	private SysMessageService sysMessageService;
	@Autowired
	private CourseScheduleDao courseScheduleDao;

	@Override
	public BaseDAO<Long, CourseHomework> getDAO() {
		return courseHomeworkDao;
	}

	@Override
	public void addCourseHomework(CourseHomework courseHomework) {
		if(Objects.isNull(courseHomework.getCourseScheduleId())){
			throw new BizException("课程不存在");
		}
		if(StringUtils.isBlank(courseHomework.getContent())){
			throw new BizException("请填写作业内容");
		}
		CourseSchedule courseSchedule = courseScheduleDao.get(courseHomework.getCourseScheduleId());
		if(Objects.isNull(courseSchedule)){
			throw new BizException("课程不存在");
		}
		Date date=new Date();
		CourseHomework oldCourseHomework = courseHomeworkDao.findByCourseSchedule(courseHomework.getCourseScheduleId());
		if(Objects.isNull(oldCourseHomework)){
			//新增课堂作业
			oldCourseHomework=courseHomework;
			oldCourseHomework.setCourseScheduleId(courseSchedule.getId());
			oldCourseHomework.setMusicGroupId(courseSchedule.getMusicGroupId());
			oldCourseHomework.setGroupType(courseSchedule.getGroupType());
			oldCourseHomework.setClassGroupId(courseSchedule.getClassGroupId());
			oldCourseHomework.setExpiryDate(DateUtil.addDays(date,7));
			oldCourseHomework.setExpectNum(courseScheduleDao.countCourseStudentNum(courseSchedule.getId()));
			courseHomeworkDao.insert(oldCourseHomework);
			List<StudentCourseHomework> studentCourseHomeworks = studentCourseHomeworkDao
					.constructInitialStudentHomeworkRecordsWithPayment(courseSchedule.getId(),
							oldCourseHomework.getId());
			if(CollectionUtils.isEmpty(studentCourseHomeworks)){
				throw new BizException("此课程没有学生");
			}
			studentCourseHomeworkDao.batchInsertStudentCourseHomeworkRecord(studentCourseHomeworks);
		}else{
			oldCourseHomework.setContent(courseHomework.getContent());
			oldCourseHomework.setAttachments(courseHomework.getAttachments());
			courseHomeworkDao.update(oldCourseHomework);
		}
	}

	@Override
	public List<Map<String, Object>> findTeacherCourseHomeworkByClassGroup(CourseHomeworkQueryInfo queryInfo) {
		Map<String, Object> params = new HashMap<>();
		MapUtil.populateMap(params, queryInfo);
		List<TeacherHomeworkListDto> dataList = null;
		List<Map<String, Object>> result = new ArrayList<>();
		int count = courseHomeworkDao.countByClassGroupAndTeacher(params);
		if (count > 0) {
			dataList = courseHomeworkDao.findByClassGroupAndTeacher(params);
			List<Long> courseIds = dataList.stream().mapToLong(TeacherHomeworkListDto::getCourseScheduleId).boxed().collect(Collectors.toList());
			List<StudentCourseHomework> allStudentCourseHomeworks = studentCourseHomeworkDao.findByCourses(courseIds);
			Map<Long, List<StudentCourseHomework>> homeworkStudentMap = allStudentCourseHomeworks.stream().collect(Collectors.groupingBy(StudentCourseHomework::getCourseScheduleId));
			for (TeacherHomeworkListDto teacherHomeworkListDto : dataList) {
				List<StudentCourseHomework> studentCourseHomeworks = homeworkStudentMap.get(teacherHomeworkListDto.getCourseScheduleId().longValue());
				if(CollectionUtils.isEmpty(studentCourseHomeworks)){
					continue;
				}
				long noRepliedNum=studentCourseHomeworks.stream().filter(e -> YesOrNoEnum.YES.equals(e.getStatus())&&YesOrNoEnum.NO.equals(e.getIsReplied())).count();
				if(noRepliedNum<=0){
					teacherHomeworkListDto.setIsReplied(YesOrNoEnum.YES.getCode());
				}
				long notSubmitNum = studentCourseHomeworks.stream().filter(e -> e.getStatus().equals(YesOrNoEnum.NO)).count();
				if(notSubmitNum<=0){
					teacherHomeworkListDto.setIsSubmit(1);
				}
				if(noRepliedNum>0){
					teacherHomeworkListDto.setStatus(1);
				}else if(noRepliedNum<=0&&notSubmitNum>0){
					teacherHomeworkListDto.setStatus(2);
				}else if(noRepliedNum<=0&&notSubmitNum<=0){
					teacherHomeworkListDto.setStatus(3);
				}
			}
		}
		if (count != 0) {
			Map<String, List<TeacherHomeworkListDto>> collect = dataList.stream().collect(Collectors.groupingBy(TeacherHomeworkListDto::getDay));
			List<Date> dates=new ArrayList<>();
			collect.keySet().forEach(ds-> dates.add(DateUtil.stringToDate(ds,"yyyy-MM-dd")));
			dates.sort(Comparator.comparing(Date::getTime));
			dates.sort(Comparator.reverseOrder());
			for (Date date : dates) {
				String key=DateUtil.dateToString(date, "yyyy-MM-dd");
				Map<String, Object> r = new HashMap<>();
				r.put("day", key);
				collect.get(key).sort(Comparator.comparing(TeacherHomeworkListDto::getStartClassTime).reversed());
				r.put("list", collect.get(key));
				result.add(r);
			}
		}
		return result;
	}

	@Override
	public void homeworkNoReplyRemind() {
		List<Mapper> list = courseHomeworkDao.queryTeacerNoReplyNum();
		for (Mapper mapper : list) {
			Map<Integer, String> receivers = new HashMap<>();
			Integer userId = (Integer) mapper.getKey();
			receivers.put(userId, userId + "");

			sysMessageService.batchSendMessage(MessageSender.JIGUANG, MessageTypeEnum.TEACHER_PUSH_JOB_WAIT_REPLY, receivers, null, 0, "6", "TEACHER",
					mapper.getValue());
		}
	}

	@Override
	@Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
	public boolean delHomwworkByCourseScheduleId(Long courseScheduleId) {
		// 删除作业
		courseHomeworkDao.delByCourseScheduleId(courseScheduleId);
		// 删除学生作业
		studentCourseHomeworkDao.delByCourseScheduleId(courseScheduleId);
		// 删除作业回复
		studentCourseHomeworkReplyDao.delByCourseScheduleId(courseScheduleId);
		return true;
	}

	@Override
	@Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
	public boolean delHomwworkByCourseScheduleId(List<Long> courseScheduleIdList) {
		// 删除作业
		courseHomeworkDao.batchDelByCourseScheduleId(courseScheduleIdList);
		// 删除学生作业
		studentCourseHomeworkDao.batchDelByCourseScheduleId(courseScheduleIdList);
		// 删除作业回复
		studentCourseHomeworkReplyDao.delByCourseScheduleIds(courseScheduleIdList);
		return true;
	}

	@Override
	public PageInfo<WebCourseHomeworkListDto> queryHomePage(CourseHomeWorkTemplateQueryInfo queryInfo) {
		PageInfo<WebCourseHomeworkListDto> pageInfo = new PageInfo<>(queryInfo.getPage(), queryInfo.getRows());
		Map<String, Object> params = new HashMap<>();
		MapUtil.populateMap(params, queryInfo);

		List<WebCourseHomeworkListDto> dataList = null;
		int count = courseHomeworkDao.findHomeCount(params);
		if (count > 0) {
			pageInfo.setTotal(count);
			params.put("offset", pageInfo.getOffset());
			dataList = courseHomeworkDao.queryHomePage(params);
			List<Long> homeWorkIds = dataList.stream().map(e -> e.getId()).collect(Collectors.toList());
			List<Map<Long,Long>> repliedList = studentCourseHomeworkDao.queryReplied(homeWorkIds);
			Map<Long,Long> map = MapUtil.convertIntegerMap(repliedList);
			dataList.forEach(e->{
				Long aLong = map.get(e.getId());
				if(aLong != null){
					e.setRepliedNum(aLong.intValue());
				}
			});
		}
		if (count == 0) {
			dataList = new ArrayList<>();
		}
		pageInfo.setRows(dataList);
		return pageInfo;
	}
}
