package com.blueland.bpm.engine.core.executor;

import org.activiti.engine.repository.ProcessDefinition;
import org.activiti.engine.runtime.ProcessInstance;
import org.activiti.engine.task.Task;
import org.springframework.stereotype.Service;

import com.blueland.bpm.common.util.ApplicationContextHolder;
import com.blueland.bpm.common.util.StringUtils;
import com.blueland.bpm.engine.config.model.Depute;
import com.blueland.bpm.engine.config.service.DeputeManager;
import com.blueland.bpm.engine.core.model.ExceptionErrorCode;
import com.blueland.bpm.engine.core.model.ProcessInputModel;
import com.blueland.bpm.engine.core.model.ProcessInstanceModel;
import com.blueland.bpm.engine.util.ProcessDefinitionUtils;
import com.blueland.bpm.engine.util.WorkFlowContants;
import com.blueland.bpm.engine.util.WorkFlowException;
import com.blueland.bpm.identity.UserService;
/**
 * 转办处理类
 * @version:  1.0
 * @author lw 
 */
@Service(WorkFlowContants.ACTION_TYPE_RECEIVER_TRANSFER)
public class ReceiverTransferExecutor extends AbstractProcessExecutor implements ProcessExecutor{
	@Override
	public ProcessInstanceModel execute(ProcessInputModel processInputModel)
			throws WorkFlowException {
		validateProcessInputModel(processInputModel);
		ProcessDefinition processDefinition = getProcessDefinition(processInputModel
				.getWf_procDefId());
		ProcessInstance processInstance = getProcessInstance(processInputModel
				.getWf_procInstId());

		additionalProcessInputModel(processInputModel, processDefinition);
		// ----------------------------------
		// 根据wfCurActInstId获取当前任务实例
		Task task = this.findTaskById(processInputModel.getWf_curActInstId());
		if (processInputModel.getWf_receiver().indexOf(",") != -1) {
			throw new WorkFlowException(ExceptionErrorCode.B2056,
					String.format("转办任务不允许有多个接收人！任务实例ID[%s],接收人[%s]",
							processInputModel.getWf_curActInstId(),
							processInputModel.getWf_receiver()));
		}
		if(processInputModel.getWf_sender()!=null){
			identityService.setAuthenticatedUserId(processInputModel.getWf_sender());
		}
		ProcessInstanceModel processInstanceModel = null;
		try {
			String receiver = existDeputeReplaceReceiver(task.getId(),processInputModel.getWf_procDefKey(), processInputModel.getWf_receiver(),
					task.getTenantId());
			// 将当前待办的接收人修改最新的receiver
			this.taskService.setAssignee(task.getId(),receiver);
			processInstanceModel = processInstanceModellBuilder
					.builderProcessInfo(processInputModel, processDefinition,
							processInstance, task);
		} catch (Exception e) {
			throw new WorkFlowException(ExceptionErrorCode.B2050,
					String.format("流程执行失败,task[%s],processInputModel[%s]",
							task, processInputModel), e);
		}
		if (StringUtils.isNotBlank(processInputModel.getWf_curComment())) {
			taskService.addComment(task.getId(), task.getProcessInstanceId(),"transfer_comment",
					processInputModel.getWf_curComment(),
					processInputModel.getWf_commentDisplayArea());
		}
		try {
			ProcessInputModel tempProcessInputModel = (ProcessInputModel) processInstanceService
					.getTaskVariables(task.getId()).get(
							WorkFlowContants.WF_PROCESS_INPUT_VARIABLE_KEY);
			tempProcessInputModel.setWf_receiver(processInputModel
					.getWf_receiver());
			ProcessDefinitionUtils.convertWf_receiver(processInputModel);
			tempProcessInputModel.setWf_receivers(processInputModel
					.getWf_receivers());
			this.taskService.setVariableLocal(task.getId(),
					WorkFlowContants.WF_PROCESS_INPUT_VARIABLE_KEY,
					tempProcessInputModel);
		} catch (Exception e) {
			throw new WorkFlowException(ExceptionErrorCode.B2050,String.format(
					"流程转办失败,task[%s],processInputModel[%s]", task,
					processInputModel), e);
		}
		// 设置返回参数
		return processInstanceModel;
	}
	
	
	/**
	 * 根据委托待办来转换receiver字段
	 * 
	 * @param processDefKey
	 * @param receiver
	 * @param appId
	 * @param delegateTask
	 * @param processInputModel
	 * @return
	 */
	public String existDeputeReplaceReceiver(String taskId,String processDefKey,String receiver, String appId) {
		try {
			UserService userService = (UserService) com.blueland.bpm.common.util.ApplicationContextHolder
					.getBean("userServiceImpl");
			com.blueland.bpm.identity.model.User userReiver = userService
					.getUserById(receiver);
			DeputeManager deputeManager = (DeputeManager) ApplicationContextHolder
					.getBean("deputeManager");
			
			Depute depute = deputeManager.getUserProcessDepute(
					userReiver.getUserCode(), processDefKey, appId);
			//判断是否存在委托关系
			if (depute == null
					|| StringUtils.isEmpty(depute.getMandataryUserId())) {//不存在直接返回原始接受人
				return receiver;
			}
			if (userService.getUserById(depute.getMandataryUserId()) != null) {//委托人是否有效
				logger.info("执行委托代办逻辑, receiver={}, mandataryUserId={},curtActInstId={}", new Object[] {
						receiver,depute.getMandataryUserId(), taskId});
				this.taskService.setOwner(taskId,receiver);//备份原始接受人
				return depute.getMandataryUserId();//返回委托人
			}
		} catch (Exception e) {
			this.logger.error("existDeputeReplaceReceiver error,taskId:"+taskId+",receiver:"+receiver, e);
		}
		return receiver;

	}

}
