package com.highdatas.mdm.service.act.impl;

import com.highdatas.mdm.entity.TUser;
import com.highdatas.mdm.pojo.NextTaskUserInfo;
import lombok.extern.slf4j.Slf4j;
import org.activiti.engine.*;
import org.activiti.engine.delegate.Expression;
import org.activiti.engine.identity.Group;
import org.activiti.engine.impl.persistence.entity.ProcessDefinitionEntity;
import org.activiti.engine.impl.pvm.process.ActivityImpl;
import org.activiti.engine.impl.task.TaskDefinition;
import org.activiti.engine.task.Task;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

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

@Slf4j
@Service
public class TaskServiceImpl extends BaseServiceImpl implements com.highdatas.mdm.service.act.TaskService{
	@Autowired
	TaskService taskService;
	@Autowired
	RepositoryService repositoryService;
	@Autowired
	HistoryService historyService;
	@Autowired
	RuntimeService runtimeService;
	@Autowired
	IdentityService identityService;
	public boolean checkClaim(String workflowId) {
		Task task = getTask(workflowId);
		if (task == null) {
			return true;
		}
		// 判断任务是否已经被签收
		if (task.getAssignee() == null) {
			return true;
		} else {
			return false;
		}
	}
	public String claimTask(String workflowId) {
		Task task = getTask(workflowId);

        TUser onlineUser = getOnlineUser();
        //resultPool = serviceCaller.getResultPool();
		
		try {
			taskService.claim(task.getId(), onlineUser.getUserId());
			//resultPool.setMessage("Task is claimed");
			return task.getId();
		}
		catch (Exception e) {
			e.printStackTrace();
			return null;
		}
	}

	
	public boolean completeTask(String taskId, boolean pass, String reason, Map<String,Object> other) {
		Map<String, Object> variables = new LinkedHashMap<String, Object>();
		if(other != null){
			Set<String> keySet = other.keySet();
			for (String key : keySet) {
				variables.put(key, other.get(key));
			}
		}
		variables.put("pass", pass);
		variables.put("reason", reason);
		try {
			taskService.setVariables(taskId, variables);
			taskService.complete(taskId,variables);

			return true;
		} 
		catch (Exception e) {
			e.printStackTrace();
			log.debug("can not complete task(" + taskId + "): " + e.getMessage());
			return false;
		}
	}	
	
	public boolean completeTask(String taskId, boolean pass, String reason) {
		return completeTask(taskId,pass,reason,null);
	}	
	
	public List<String> getTodoTask()  {
        TUser onlineUser = getOnlineUser();
        Set<String> result = new HashSet<>();
		//List<Task> list1 = TimeTaskService.createTaskQuery().active().list();
		List<Task> list = taskService.createTaskQuery().taskAssignee(onlineUser.getUserId()).active().list();

		result.addAll(list.stream().map(task -> task.getProcessInstanceId()).collect(Collectors.toList()));

		List<Task> toClaimList = taskService.createTaskQuery().taskCandidateUser(onlineUser.getUserId()).active().list();

		result.addAll(toClaimList.stream().map(task -> task.getProcessInstanceId()).collect(Collectors.toList()));


		List<Group> groups = identityService.createGroupQuery().groupMember(onlineUser.getUserId()).list();
        List<String> groupIds = groups.stream().map(Group::getId).collect(Collectors.toList());
        toClaimList = taskService.createTaskQuery().taskCandidateGroupIn(groupIds).active().list();

		result.addAll(toClaimList.stream().map(task -> task.getProcessInstanceId()).collect(Collectors.toList()));

		return new ArrayList<>(result);
	}
    
    public Task geTask(String processId) {
    	Task task = taskService.createTaskQuery().processInstanceId(processId).singleResult();
    	return task;
	}

	@Override
	public NextTaskUserInfo getNestTaskAssignee(String workflowId) {
		//TODO 需修改
		NextTaskUserInfo nextTaskUserInfo = new NextTaskUserInfo();
		Task nextTask = geTask(workflowId);
		String nextTaskAssignee = nextTask.getAssignee();
		if (!StringUtils.isEmpty(nextTaskAssignee)) {
			nextTaskUserInfo.setUserId(nextTaskAssignee);
			nextTaskUserInfo.setRoleId("R001");
			return nextTaskUserInfo;
		}
		String processDefinitionId=nextTask.getProcessDefinitionId(); // 获取流程定义id

		ProcessDefinitionEntity processDefinitionEntity= (ProcessDefinitionEntity) repositoryService.getProcessDefinition(processDefinitionId);

		ActivityImpl activityImpl=processDefinitionEntity.findActivity(nextTask.getTaskDefinitionKey()); // 根据活动id获取活动实例
		TaskDefinition taskDef = (TaskDefinition)activityImpl.getProperties().get("taskDefinition");
		Set<Expression> userCodes = taskDef.getCandidateUserIdExpressions();//候选人
		Set<Expression> roleCodes = taskDef.getCandidateGroupIdExpressions();//候选组
		if (roleCodes.size() != 0) {
			String roleId = roleCodes.stream().map(expression -> expression.getExpressionText()).findFirst().get();
			nextTaskUserInfo.setRoleId(roleId);
		}
		return nextTaskUserInfo;
	}

}