package com.yeejoin.precontrol.common.task;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.yeejoin.precontrol.common.entity.Person;
import com.yeejoin.precontrol.common.entity.PersonMessage;
import com.yeejoin.precontrol.common.entity.Project;
import com.yeejoin.precontrol.common.entity.TaskRiskControl;
import com.yeejoin.precontrol.common.enums.*;
import com.yeejoin.precontrol.common.mapper.TaskRiskControlMapper;
import com.yeejoin.precontrol.common.publish.MessageEventPublish;
import com.yeejoin.precontrol.common.service.*;
import com.yeejoin.precontrol.common.utils.PersonUtils;
import com.yeejoin.precontrol.common.vo.PersonVo;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Set;
import java.util.stream.Collectors;

/**
 * @author DELL
 */
@Component
@EnableScheduling
@Slf4j
public class TaskWarningTask {

	@Autowired
	ITaskSalaryConfirmService iTaskSalaryConfirmService;

	@Autowired
	IPersonMessageService IPersonMessageService;

	@Autowired
	ITaskRiskControlService iTaskRiskControlService;

	@Autowired
	MessageEventPublish messageEventPublish;

	@Autowired
	TaskRiskControlMapper taskRiskControlMapper;

	@Autowired
	IPersonService iPersonService;

	@Autowired
	IProjectService iProjectService;

	@Autowired
	SmallProService smallProService;
	
	@Autowired
	PersonUtils personUtils;

	@Scheduled(cron = "0 0 8 * * ?")
	public void scan() {
		log.info("定时任务计算人员3天是否未处理薪资任务开始--------------->");
		List<PersonVo> list = iTaskSalaryConfirmService.warnPersons(3);
		List<PersonMessage> messageList = new ArrayList<>();
		list.forEach(item -> {
			PersonMessage message = new PersonMessage();
			message.setContent(MessageTypeEnum.SALARY.getName());
			message.setPersonId(item.getId());
			message.setProjectId(item.getProjectId());
			message.setObjectId(item.getTaskPersonId());
			message.setType(MessageTypeEnum.SALARY.getType());
			message.setSubType((long) MessageSalaryTypeEnum.OVERTIME.getType());
			messageList.add(message);
		});
		IPersonMessageService.saveBatch(messageList);
		log.info("定时任务计算人员3天是否未处理薪资任务结束--------------->");
	}

	@Scheduled(cron = "0 0 8 * * ?")
	public void overtimeNotice() {
		List<TaskRiskControl> overtimeTask = iTaskRiskControlService.list(new LambdaQueryWrapper<TaskRiskControl>()
				.lt(TaskRiskControl::getStage, 99).lt(TaskRiskControl::getEndTime, new Date()));
		JSONArray jsonArray = new JSONArray();
		overtimeTask.forEach(t -> {
			JSONObject msg = new JSONObject();
			msg.put(MessageAttributeEnum.MSG_TYPE.getName(), MessageTypeEnum.SERVICE_REMINDER.getType());
			msg.put(MessageAttributeEnum.MSG_SUB_TYPE.getName(),
					MessageSubTypeEnum.SERVICE_REMINDER_RISK_WORK_OVERDUE.getType());
			msg.put(MessageAttributeEnum.CONTENT.getName(),
					MessageSubTypeEnum.SERVICE_REMINDER_RISK_WORK_OVERDUE.getTip());
			msg.put(MessageAttributeEnum.PERSON_ID.getName(), t.getSecPersonId());
			msg.put(MessageAttributeEnum.PARAM.getName(), t.getStage());
			msg.put(MessageAttributeEnum.TASK_ID.getName(), t.getId());
			jsonArray.add(msg);
		});
		if (jsonArray.size() > 0) {
			JSONObject obj = new JSONObject();
			obj.put("param", jsonArray);
			messageEventPublish.publish(obj);
		}
		
		overtimeTask.forEach(t -> {
			Person secPerson = iPersonService.getById(t.getSecPersonId());
			Project project = iProjectService.getById(t.getProjectId());
			Set<Long> set =  personUtils.getDefaultPerson(t.getProjectId());
			// 微信服务通知
			List<Person> persons = iPersonService.list(new LambdaQueryWrapper<Person>()
					.in(Person::getId, set).isNotNull(Person::getOpenId));
			List<String> openIds = persons.stream().map(Person::getOpenId).collect(Collectors.toList());
			List<String> messages = new ArrayList<>();
			messages.add(project.getName());
			messages.add(t.getName());
			messages.add(String.valueOf(t.getEndTime()));
			messages.add(secPerson.getName());
			smallProService.sendWeChatUpcomingMessage(openIds, WeChatMsgTemplateTypeEum.TODO_OVERTIME.getValue(),
					messages);
		});
		
		if (log.isInfoEnabled()) {
			log.info("风险超时到期未办理，每日8时进行提醒，定时任务处理完成:{}", jsonArray.toJSONString());
		}
	}

	@Scheduled(cron = "0 0 8 * * ?")
	public void waitDeal() {
		List<TaskRiskControl> waitDealTask = taskRiskControlMapper.waitDealTaskList();
		JSONArray jsonArray = new JSONArray();
		waitDealTask.forEach(t -> {
			JSONObject msg = new JSONObject();
			msg.put(MessageAttributeEnum.MSG_TYPE.getName(), MessageTypeEnum.SERVICE_REMINDER.getType());
			msg.put(MessageAttributeEnum.MSG_SUB_TYPE.getName(), MessageSubTypeEnum.RISK_WORK_EXPIRE.getType());
			msg.put(MessageAttributeEnum.CONTENT.getName(), t.getName());
			msg.put(MessageAttributeEnum.PERSON_ID.getName(), t.getSecPersonId());
			msg.put(MessageAttributeEnum.PARAM.getName(), t.getStage());
			msg.put(MessageAttributeEnum.TASK_ID.getName(), t.getId());
			jsonArray.add(msg);
		});
		if (jsonArray.size() > 0) {
			JSONObject obj = new JSONObject();
			obj.put("param", jsonArray);
			messageEventPublish.publish(obj);
		}

		waitDealTask.forEach(t -> {
			Person secPerson = iPersonService.getById(t.getSecPersonId());
			Project project = iProjectService.getById(t.getProjectId());
			Set<Long> set =  personUtils.getDefaultPerson(t.getProjectId());
			// 微信服务通知
			List<Person> persons = iPersonService.list(new LambdaQueryWrapper<Person>()
					.in(Person::getId, set).isNotNull(Person::getOpenId));
			List<String> openIds = persons.stream().map(Person::getOpenId).collect(Collectors.toList());
			List<String> messages = new ArrayList<>();
			messages.add(secPerson.getName());
			messages.add(t.getName());
			messages.add(project.getName());
			messages.add(String.valueOf(t.getStartTime()));
			smallProService.sendWeChatUpcomingMessage(openIds, WeChatMsgTemplateTypeEum.PROJECT_WARN.getValue(),
					messages);
		});

		if (log.isInfoEnabled()) {
			log.info("风险到期未办理，每日8时进行提醒；结束日期后不告警:{}", jsonArray.toJSONString());
		}
	}
}
