package com.blueland.bpm.manage.web;

import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import cn.hutool.core.util.StrUtil;
import com.blueland.bpm.application.model.ApplicationEntity;
import com.blueland.bpm.application.service.ApplicationManager;
import com.blueland.bpm.identity.UserService;
import org.activiti.engine.impl.cmd.AddCommentByExtendCmd;
import org.activiti.engine.impl.cmd.UpdateCommentCmd;
import org.activiti.engine.impl.identity.Authentication;
import org.activiti.engine.impl.persistence.entity.HistoricProcessInstanceEntity;
import org.activiti.engine.impl.persistence.entity.TaskEntity;
import org.activiti.engine.impl.util.json.JSONObject;
import org.activiti.engine.task.Task;
import org.activiti.engine.task.TaskQuery;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.servlet.ModelAndView;

import com.blueland.bpm.common.page.Page;
import com.blueland.bpm.common.page.PageRequest;
import com.blueland.bpm.engine.config.service.ActivityInfoConfigManager;
import com.blueland.bpm.engine.core.model.ActivityDefinitionModel;
import com.blueland.bpm.engine.core.model.ActivityInstanceModel;
import com.blueland.bpm.engine.core.model.BusinessDataObject;
import com.blueland.bpm.engine.core.model.ProcessInputModel;
import com.blueland.bpm.engine.core.model.ProcessLogModel;
import com.blueland.bpm.engine.core.model.ProcessPageContext;
import com.blueland.bpm.engine.core.model.SearchProcessListDTO;
import com.blueland.bpm.engine.core.service.ProcessConfigService;
import com.blueland.bpm.engine.core.service.ProcessDefinitionService;
import com.blueland.bpm.engine.core.service.ProcessInstanceService;
import com.blueland.bpm.engine.core.service.ProcessOperateFacade;
import com.blueland.bpm.engine.util.PageFieldsUtil;
import com.blueland.bpm.engine.util.WorkFlowContants;
import com.blueland.bpm.identity.model.User;
import com.blueland.bpm.manage.config.web.UserTreeManager;
import com.blueland.bpm.manage.util.BaseUser;
import com.blueland.bpm.manage.util.MyContants;
import com.blueland.bpm.manage.util.TreeNode;

@Controller
@RequestMapping(value = "/taskMgr")
public class TaskController extends BaseProcessController {
	@Autowired
	private ProcessInstanceService processInstanceService;
	@Autowired
	private ProcessConfigService processConfigService;
	@Autowired
	private ProcessDefinitionService processDefinitionService;
	@Autowired
	private ActivityInfoConfigManager activityInfoConfigManager;
	@Autowired
	ProcessOperateFacade processOperateFacade;
	/*
	 * @Autowired ProcessUserOrgMatchService processUserOrgMatchService;
	 */
	@Autowired
	private UserTreeManager userTreeManager;
	@Autowired
	private UserService userService;
	@Autowired
	private ApplicationManager applicationManager;
	/**
	 * 查询待办任务列表
	 * 
	 * @param pageRequest
	 * @param request
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/list")
	public ModelAndView taskList(String tenantId,String assignee,String assigneeName,String actDefId,String actInstId,
								 String customSso, SearchProcessListDTO pageRequest, HttpServletRequest request, HttpServletResponse response) throws Exception {
		if("1".equals(customSso)){
			HttpSession session = request.getSession(true);
			session.setAttribute("customSso", customSso);

			User user = userService.getUserById("admin");
			BaseUser bUser = BaseUser.getInstance();
			if(user!=null && StrUtil.isNotEmpty(user.getUserId())){
				bUser.cleanCookieUser(request, response);
				bUser.setCookieUser(response, BaseUser.toUpperCase(user.getUserId()));
				List<ApplicationEntity> list = applicationManager.selectByUserId("admin");
				bUser.saveUserToSession(request, user, list);
			}
		}

		TaskQuery query = processInstanceService.getTaskService()
				.createTaskQuery();
		String appId = "";
		if(StringUtils.isNotEmpty(tenantId)){
			appId= tenantId;
		}else{
			appId = BaseUser.getInstance().getLoginUserAppId(request);
		}
		boolean isBpmAdmin = BaseUser.isEbpmAdmin(BaseUser.getInstance()
				.getSessionUser(request));

		if ("true".equalsIgnoreCase(MyContants.IS_OPEN_TENANT)
				&& (!StringUtils.isEmpty(appId))) {
			query.taskTenantId(appId);
		}
		pageRequest = (SearchProcessListDTO) bindPageRequest(request,
				pageRequest, "");
		if (StringUtils.isNotEmpty(pageRequest.getProcessDefId())) {
			query.processDefinitionId(pageRequest.getProcessDefId());

		}
		if (StringUtils.isNotEmpty(pageRequest.getProcessInstanceId())) {
			query.processInstanceId(pageRequest.getProcessInstanceId());
		}
		if (StringUtils.isNotEmpty(pageRequest.getProcessDefName())) {//增加流程定义名称模糊查询
			query.processDefinitionNameLike("%"+pageRequest.getProcessDefName()+"%");
		}
		if (StringUtils.isNotEmpty(actDefId)) {
			query.taskDefinitionKeyLike("%"+actDefId+"%");
		}
		if (StringUtils.isNotEmpty(pageRequest.getTitle())) {
			query.procTitle("%"+pageRequest.getTitle()+"%");

		}

		if (StringUtils.isNotEmpty(actInstId)) {
			query.taskId(actInstId);
		}
		if (!StringUtils.isEmpty(assignee)) {
			query.taskAssignee(assignee);
		}
		Page<Task> page = new Page<Task>(pageRequest, (int) query.count());
		List<Task> tasks = query.orderByTaskCreateTime().desc()
				.listPage(page.getFirstResult(), page.getPageSize());
		/*for (Task task : tasks) {
			try {
				TaskEntity taskEntity = (TaskEntity) task;
				String desc = "";
				ActivityInfoConfig activityInfoConfig = activityInfoConfigManager
						.getActivityInfoConfig(
								taskEntity.getProcessDefinitionId(),
								taskEntity.getTaskDefinitionKey());
				if (activityInfoConfig.getActivityLimitTime() != null
						&& activityInfoConfig.getActivityLimitTime() != 0) {
					Date dueDate = DateUtils.addDays(
							taskEntity.getCreateTime(),
							activityInfoConfig.getActivityLimitTime());
					long limitDate = differByDay(dueDate, new Date());
					if (limitDate > 0) {
						desc = "超时" + limitDate + "天";
					} else {
						desc = "剩余" + Math.abs(limitDate) + "天";
					}

				} else {
					desc = "耗时"
							+ differByDay(taskEntity.getCreateTime(),
									new Date()) + "天";
					;
				}
				taskEntity.setDescription(desc);
			} catch (Exception e) {
				e.printStackTrace();
			}
		}*/
		page.setResult(tasks);
		ModelAndView modelAndView = new ModelAndView("/taskMgr/list");
		modelAndView.addAllObjects(toModelMap(page, pageRequest));
		modelAndView.addObject("assignee", assignee);
		modelAndView.addObject("actDefId", actDefId);
		modelAndView.addObject("actInstId", actInstId);
		modelAndView.addObject("assigneeName", assigneeName);
		modelAndView.addObject("isBpmAdmin", isBpmAdmin);
		return modelAndView;
	}
	
	

	/**
	 * 自由跳转任务界面
	 * 
	 * @param taskId
	 * @param request
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/jumpAnyTaskView")
	public ModelAndView jumpAnyTaskView(String taskId,
			HttpServletRequest request) throws Exception {
		ActivityInstanceModel actInstModel = processInstanceService
				.getTask(taskId);
		// 获取流程数据
		Map<String, Object> processModel = processOperateFacade
				.getProcessToDoDetail(actInstModel.getProcDefId(), actInstModel
						.getProcInstId(), actInstModel.getActInstId(),
						actInstModel.getActivityDefinition().getActDefId(),
						BaseUser.getInstance().getSessionUser(request)
								.getUserId(), BaseUser.getInstance()
								.getSessionUser(request).getOrgId(), false);
		ModelAndView modelAndView = new ModelAndView("/taskMgr/baseProcessPage");
		modelAndView.addAllObjects(processModel);
		MyContants.saveUserOperate(request, "taskId", true, "自由跳转操作成功",
				MyContants.LOGIN_SESSION_USER, MyContants.APPLICATION);
		return modelAndView;
	}

	/**
	 * 自由跳转
	 * 
	 * @param tempProcessInputModel
	 * @param request
	 * @return
	 */
	@RequestMapping(value = "/jumpAnyTask",method=RequestMethod.POST)
	@ResponseBody
	public Map<String, Object> nextExecute(
			ProcessInputModel tempProcessInputModel, HttpServletRequest request) {
		ActivityInstanceModel activityInstanceModel = processInstanceService
				.getTask(tempProcessInputModel.getWf_curActInstId());
		if (activityInstanceModel == null) {
			return null;
		}
		ProcessInputModel processInputModel = (ProcessInputModel) processInstanceService
				.getTaskVariables(activityInstanceModel.getActInstId()).get(
						WorkFlowContants.WF_PROCESS_INPUT_VARIABLE_KEY);
		processInputModel
				.setWf_actionType(WorkFlowContants.ACTION_TYPE_EXECUTE_ACTIVITY);
		processInputModel.setWf_receivers(tempProcessInputModel
				.getWf_receivers());
		processInputModel.setWf_receiver("");
		processInputModel.setWf_nextActDefId(tempProcessInputModel
				.getWf_nextActDefId());
		processInputModel.setWf_nextActDefName(tempProcessInputModel
				.getWf_nextActDefName());
		processInputModel.setWf_nextActDefType(tempProcessInputModel
				.getWf_nextActDefType());
		processInputModel.setWf_curActInstId(activityInstanceModel
				.getActInstId());
		processInputModel.setWf_curActDefId(activityInstanceModel
				.getActivityDefinition().getActDefId());
		processInputModel.setWf_curActDefName(activityInstanceModel
				.getActivityDefinition().getActDefName());
		processInputModel.setWf_procDefId(activityInstanceModel.getProcDefId());
		processInputModel.setWf_procTitle(activityInstanceModel.getProcTitle());
		processInputModel.setWf_procInstId(activityInstanceModel
				.getProcInstId());
		processInputModel.setWf_sender(activityInstanceModel.getReceiver());
		processInputModel.setWf_sendUserId(activityInstanceModel
				.getReceiverUserId());
		processInputModel.setWf_sendUserName(activityInstanceModel.getReceiverUserName());
		processInputModel.setWf_sendUserOrgId(activityInstanceModel
				.getReceiverOrgId());
		processInputModel.setWf_sendUserOrgName(activityInstanceModel.getReceiverOrgName());
		processInputModel.setWf_curComment("");
		processInputModel.setWf_commentDisplayArea("");
		Map<String, Object> resultMap = processOperateFacade
				.nextExecute(processInputModel);
		return resultMap;
	}

	/**
	 * 更新待办数据界面
	 * 
	 * @param taskId
	 * @param request
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/updateTaskDataView")
	public ModelAndView updateTaskDataView(String taskId,
			HttpServletRequest request) throws Exception {

		ActivityInstanceModel actInstModel = processInstanceService
				.getTask(taskId);
		// 获取流程数据
		String fields = (String) processInstanceService.getTaskVariables(
				actInstModel.getActInstId())
				.get(WorkFlowContants.WF_FIELDS_KEY);
		BusinessDataObject businessDataObject = processInstanceService
				.getBusinessDataObject(actInstModel.getProcInstId());
		ModelAndView modelAndView = new ModelAndView("/taskMgr/updateTaskData");
		modelAndView.addObject("businessDataObject", businessDataObject);
		modelAndView.addObject("fields", fields);
		modelAndView.addObject("wf_curActInstId", taskId);
		return modelAndView;
	}

	/**
	 * 更新待办数据
	 * 
	 * @param request
	 * @param wf_curActInstId
	 * @param wf_dataType
	 * @param wf_objectType
	 * @param wf_xmlRootName
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/updateTaskFieldsData",method=RequestMethod.POST)
	@ResponseBody
	public String updateTaskFieldsData(HttpServletRequest request,
			String wf_curActInstId) throws Exception {
		Map<String, Object> fieldMaps = getParametersNoStartingWith(request,
				WorkFlowContants.WF_PAGE_INPUT_PREFIX);
		String fields = PageFieldsUtil.fieldsToXml(fieldMaps);
		processOperateFacade
				.getProcessExecuteService()
				.getTaskService()
				.setVariable(wf_curActInstId, WorkFlowContants.WF_FIELDS_KEY,
						fields);
		/*
		 * MyContants.saveUserOperate(request,
		 * "wf_curActInstId;wf_dataType;wf_objectType;wf_xmlRootName", true,
		 * "修改业务属性操作成功", MyContants.LOGIN_SESSION_USER,MyContants.APPLICATION);
		 */
		return this.ACTION_SUCCESS;
	}

	/**
	 * 更新待办数据
	 * 
	 * @param request
	 * @param wf_curActInstId
	 * @param wf_dataType
	 * @param wf_objectType
	 * @param wf_xmlRootName
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/updateTaskBusinessDataObject",method=RequestMethod.POST)
	@ResponseBody
	public String updateTaskBusinessDataObject(HttpServletRequest request,
			String wf_curActInstId, String wf_dataType, String wf_objectType,
			String wf_xmlRootName) throws Exception {
		Map<String, Object> fields = getParametersNoStartingWith(request,
				WorkFlowContants.WF_PAGE_INPUT_PREFIX);
		BusinessDataObject dataObject = new BusinessDataObject();
		dataObject.setObjectType(wf_objectType);
		if (wf_dataType.equals("xml")) {
			StringBuffer xmlBuf = new StringBuffer();
			if (fields == null || fields.isEmpty())
				return xmlBuf.toString();
			xmlBuf.append("<" + wf_xmlRootName + ">");
			for (Map.Entry<String, Object> entryField : fields.entrySet()) {
				xmlBuf.append("<");
				xmlBuf.append(entryField.getKey());
				xmlBuf.append(">");
				xmlBuf.append(entryField.getValue());
				xmlBuf.append("</");
				xmlBuf.append(entryField.getKey());
				xmlBuf.append(">");
			}
			xmlBuf.append("</" + wf_xmlRootName + ">");
			dataObject.setBizData(xmlBuf.toString());
		} else if (wf_dataType.equals("json")) {
			JSONObject json = new JSONObject(fields);
			dataObject.setBizData(json.toString());
		} else
			dataObject.setBizData((String) request.getParameter("txtBizData"));
		ActivityInstanceModel actInstModel = processInstanceService
				.getTask(wf_curActInstId);

		processOperateFacade
				.getProcessExecuteService()
				.getRuntimeService()
				.setVariable(actInstModel.getExecutionId(),
						WorkFlowContants.WF_BUSINESS_DATA_OBJECT_KEY,
						dataObject);
		/*
		 * MyContants.saveUserOperate(request,
		 * "wf_curActInstId;wf_dataType;wf_objectType;wf_xmlRootName", true,
		 * "修改业务属性操作成功", MyContants.LOGIN_SESSION_USER,MyContants.APPLICATION);
		 */
		return this.ACTION_SUCCESS;
	}

	/**
	 * 更新待办意见界面
	 * 
	 * @param taskId
	 * @param request
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/updateProcessCommentView")
	public ModelAndView updateProcessCommentView(String procInstId,
			HttpServletRequest request) throws Exception {
	
		List<ProcessLogModel> processComments = processInstanceService
				.getProcessComments(procInstId);
		ModelAndView modelAndView = new ModelAndView(
				"/taskMgr/updateProcessComment");
		modelAndView.addObject("processComments", processComments);
		modelAndView.addObject("procInstId", procInstId);
		return modelAndView;
	}

	/**
	 * 删除流程意见
	 * 
	 * @param taskId
	 * @param request
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/deleteProcessComment",method=RequestMethod.POST)
	@ResponseBody
	public boolean deleteProcessComment(String procInstId,String commentId,HttpServletRequest request) throws Exception {
		this.processInstanceService.getTaskService().deleteComment(commentId);
		MyContants.saveUserOperate(request, "taskId", true, "删除流转意见操作成功",
				MyContants.LOGIN_SESSION_USER, MyContants.APPLICATION);
		return true;
	}
	
	/**
	 * 更新流程意见
	 * 
	 * @param taskId
	 * @param request
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/updateProcessComment",method=RequestMethod.POST)
	public ModelAndView updateProcessComment(String procInstId,
			HttpServletRequest request) throws Exception {
		// 执行流程
		Map<String, Object> fieldsMap = getParametersNoStartingWith(request,
				WorkFlowContants.WF_PAGE_INPUT_PREFIX);
		for (Entry<String, Object> fieldEntry : fieldsMap.entrySet()) {
			if (fieldEntry.getKey().indexOf("commentId_") != -1) {
				String commentId = fieldEntry.getKey().split("_")[1];
				String commentValue = (String) fieldEntry.getValue();
				if (StringUtils.isEmpty(commentId)
						|| StringUtils.isEmpty(commentValue)) {
					continue;
				}
				processInstanceService.getManagementService().executeCommand(
						new UpdateCommentCmd( commentId, commentValue));
			}
		}
		MyContants.saveUserOperate(request, "taskId", true, "修改流转意见操作成功",
				MyContants.LOGIN_SESSION_USER, MyContants.APPLICATION);
		return this.updateProcessCommentView(procInstId, request);
	}
	
	
	/**
	 * 更新指定流程环节意见
	 * 
	 * @param taskId
	 * @param request
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/addComment",method=RequestMethod.POST)
	@ResponseBody
	public String addComment(String taskId,String userId,String msg,HttpServletRequest request) throws Exception {
		ActivityInstanceModel act = processInstanceService.getHistoryTask(taskId);
		if (act == null) {
			return "无法找到该环节实例，请确保该环节ID不是待办ID";
		}
		act.getActivityDefinition().setActivityInfoConfig(activityInfoConfigManager.getActivityInfoConfig(act.getProcDefId(),act.getActDefId()));
		Authentication.setAuthenticatedUserId(userId);
		processInstanceService.getManagementService().executeCommand(
				new AddCommentByExtendCmd(taskId, act.getProcInstId(), msg, act.getActivityDefinition().getActivityInfoConfig().getIdeaDisplayArea()));	
		MyContants.saveUserOperate(request, "taskId", true, "新增流转意见操作成功",
				MyContants.LOGIN_SESSION_USER, MyContants.APPLICATION);
		return "true";
	}

	/**
	 * 退回起草环节
	 * 
	 * @param taskId
	 * @param request
	 * @return
	 */
	@RequestMapping(value = "/backStarterTask")
	@ResponseBody
	public Map<String, Object> backStarterTask(String taskId,
			HttpServletRequest request) {
		ActivityInstanceModel activityInstanceModel = processInstanceService
				.getTask(taskId);
		if (activityInstanceModel == null) {
			return null;
		}
		ProcessInputModel processInputModel = (ProcessInputModel) processInstanceService
				.getTaskVariables(activityInstanceModel.getActInstId()).get(
						WorkFlowContants.WF_PROCESS_INPUT_VARIABLE_KEY);
			processInputModel
				.setWf_actionType(WorkFlowContants.ACTION_TYPE_CALLBACK_START_ACTIVITY);
		processInputModel.setWf_curActInstId(activityInstanceModel
				.getActInstId());
		processInputModel
				.setWf_curActDefId(activityInstanceModel.getActDefId());
		processInputModel.setWf_curActDefName(activityInstanceModel
				.getActDefName());
		processInputModel.setWf_procDefId(activityInstanceModel.getProcDefId());
		processInputModel.setWf_procTitle(activityInstanceModel.getProcTitle());
		processInputModel.setWf_procInstId(activityInstanceModel
				.getProcInstId());
		
		processInputModel.setWf_sender(activityInstanceModel.getReceiver());
		processInputModel.setWf_sendUserId(activityInstanceModel
				.getReceiverUserId());
		processInputModel.setWf_sendUserName(activityInstanceModel.getReceiverUserName());
		processInputModel.setWf_sendUserOrgId(activityInstanceModel
				.getReceiverOrgId());
		processInputModel.setWf_sendUserOrgName(activityInstanceModel.getReceiverOrgName());
		/*processInputModel.setWf_curComment("");
		processInputModel.setWf_commentDisplayArea("");*/
		
		Map<String, Object> resultMap = processOperateFacade
				.nextExecute(processInputModel);
		return resultMap;
	}

	/**
	 * 获取数据权限
	 * 
	 * @param butOperateId
	 * @param curActInstId
	 * @param curProcInstId
	 * @param request
	 * @return
	 */
	@RequestMapping(value = "/getButOperatePower")
	@ResponseBody
	public Boolean getButOperatePower(String butOperateId, String curActInstId,
			String curProcInstId, HttpServletRequest request) {
		boolean result = false;
		Map<String, Object> pageDetailVaribale = new HashMap<String, Object>();
		try {
			ActivityInstanceModel task = null;
			User user = BaseUser.getInstance().getSessionUser(request);
			ProcessPageContext processPageContext = new ProcessPageContext(
					WorkFlowContants.TODO_OPEN_PAGE_TYPE,
					WorkFlowContants.ACTION_TYPE_EXECUTE_ACTIVITY, "",
					user.getUserId(), user.getOrgId());
			try{
				//流程作废有可能没有task
			task = processInstanceService.getTask(curActInstId);
			}catch(Exception e){
				
			}
			if(StringUtils.isEmpty(curProcInstId)&&task!=null){
				curProcInstId=task.getProcInstId();
			}
			if(task==null){
				List<ActivityInstanceModel> tasks=processInstanceService.getProcessAllTasks(curProcInstId);
				task=tasks.isEmpty()?null:tasks.get(0);
			}
			if(butOperateId.equals("ADD_MULTIINST_ACT_BTN")){
				task=processInstanceService.getHistoryTask(task.getActInstId());
			}else if(butOperateId.equals("DELETE_MULTIINST_ACT_BTN")){
				task=processInstanceService.getHistoryTask(task.getActInstId());
			}
			HistoricProcessInstanceEntity processInstance = (HistoricProcessInstanceEntity) processInstanceService
					.getHistoryService()
					.createHistoricProcessInstanceQuery()
					.processInstanceId(curProcInstId).singleResult();
			pageDetailVaribale
					.put("processPageContext", processPageContext);
			pageDetailVaribale.put("processInstance", processInstance);
			pageDetailVaribale.put("task", task);

			// 判断按钮是否有权限
			result = processConfigService.hasActivityButOperatePower(
					butOperateId, pageDetailVaribale);
		} catch (Exception e) {
			e.printStackTrace();
		}
		return result;
	}

	/**
	 * 退回上一步
	 * 
	 * @param taskId
	 * @param request
	 * @return
	 */
	@RequestMapping(value = "/backPrevTask",method=RequestMethod.POST)
	@ResponseBody
	public Map<String, Object> backPrevTask(String taskId,
			HttpServletRequest request) {
		ActivityInstanceModel activityInstanceModel = processInstanceService
				.getTask(taskId);
		if (activityInstanceModel == null) {
			return null;
		}
		ProcessInputModel processInputModel = (ProcessInputModel) processInstanceService
				.getTaskVariables(activityInstanceModel.getActInstId()).get(
						WorkFlowContants.WF_PROCESS_INPUT_VARIABLE_KEY);
		processInputModel
				.setWf_actionType(WorkFlowContants.ACTION_TYPE_CALLBACK_PREV_ACTIVITY);
		processInputModel.setWf_curActInstId(activityInstanceModel
				.getActInstId());
		processInputModel.setWf_curActDefId(activityInstanceModel
				.getActivityDefinition().getActDefId());
		processInputModel.setWf_curActDefName(activityInstanceModel
				.getActivityDefinition().getActDefName());
		processInputModel.setWf_procDefId(activityInstanceModel.getProcDefId());
		processInputModel.setWf_procTitle(activityInstanceModel.getProcTitle());
		processInputModel.setWf_procInstId(activityInstanceModel
				.getProcInstId());
		
		processInputModel.setWf_sender(activityInstanceModel.getReceiver());
		processInputModel.setWf_sendUserId(activityInstanceModel
				.getReceiverUserId());
		processInputModel.setWf_sendUserName(activityInstanceModel.getReceiverUserName());
		processInputModel.setWf_sendUserOrgId(activityInstanceModel
				.getReceiverOrgId());
		processInputModel.setWf_sendUserOrgName(activityInstanceModel.getReceiverOrgName());
		Map<String, Object> resultMap = processOperateFacade
				.nextExecute(processInputModel);
		MyContants.saveUserOperate(request, "taskId", true, "退回上一环节成功",
				MyContants.LOGIN_SESSION_USER, MyContants.APPLICATION);
		return resultMap;
	}

	/**
	 * 获取下一步活动信息
	 * 
	 * @param processDefinitionId
	 * @param activityId
	 * @param userId
	 * @return
	 */
	@RequestMapping(value = "getNextActivity")
	@ResponseBody
	public List<TreeNode> getNextActivity(String processDefinitionId,
			String activityId, String userId, String pageInputVar) {
		List<ActivityDefinitionModel> activityNodes = processDefinitionService
				.getProcessUserActivitys(processDefinitionId);
		List<TreeNode> treeNodes = new ArrayList<TreeNode>();
		for (ActivityDefinitionModel activity : activityNodes) {
			if (activity.getActDefId().equals(activityId)) {
				continue;
			}
			TreeNode treeNode = new TreeNode(activity.getActDefId(),
					activity.getActDefId(), activity.getActDefName(), false,
					activity.getActType(), activity.isMulti(),
					activity.isNotSelectReceiver());
			treeNodes.add(treeNode);
		}
		return treeNodes;
	}

	/**
	 * 获取下一步活动对应的人员树
	 * 
	 * @param processDefinitionId
	 * @param curActivityId
	 * @param destActivityId
	 * @param userId
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "getNextActivityUserTree")
	@ResponseBody
	public List<TreeNode> getNextActivityUserTree(HttpServletRequest request,
			String processDefinitionId, String processInstId,
			String curActInstId, String curActivityId, String destActivityId,
			String userId, String userOrgId) throws Exception {
		/*List<ActivityResourceModel> activityUserNodes = processDefinitionService
				.getActivityUserTree(processInstId, processDefinitionId,
						curActInstId, curActivityId, destActivityId, BaseUser
								.getInstance().getSessionUser(request)
								.getUserId(), BaseUser.getInstance()
								.getSessionUser(request).getOrgId(), null, null);
		List<TreeNode> treeNodes = new ArrayList<TreeNode>();
		if (activityUserNodes == null)
			return treeNodes;
		for (ActivityResourceModel activityResource : activityUserNodes) {
			boolean isParent = false;
			if (activityResource.getType().equals("ORG")
					&& activityResource.getLevel() < 1) {
				isParent = true;
			}
			TreeNode treeNode = new TreeNode(activityResource.getId(),
					activityResource.getParentId(), activityResource.getName(),
					isParent, activityResource.getType(), false, false);
			treeNodes.add(treeNode);
		}*/
		List<TreeNode> treeNodes=userTreeManager.getUserOrgTree(MyContants.TOP_ORG_ID,false,"USER","","",true,"");
		
		return treeNodes;
	}

	/**
	 * 删除待办数据
	 * 
	 * @param taskId
	 * @param request
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/delete",method=RequestMethod.POST)
	@ResponseBody
	public String delete(String taskId, HttpServletRequest request)
			throws Exception {
		ActivityInstanceModel activityInstanceModel = processInstanceService
				.getTask(taskId);
		if (activityInstanceModel == null) {
			return this.ACTION_ERROR;
		}
		processInstanceService.getTaskService().deleteTaskAndExecution(taskId);
		return this.ACTION_SUCCESS;
	}

	public static long differByDay(Date startDate, Date endDate) {
		if (startDate == null || endDate == null) {
			return 0;
		}
		return (endDate.getTime() / 86400000 - startDate.getTime() / 86400000);
	}

	/**
	 * 重新分配人员界面
	 * 
	 * @param taskId
	 * @param request
	 * @return
	 */
	@RequestMapping(value = "/againSetTaskReceiverView")
	public ModelAndView againSetTaskReceiverView(String taskId,
			HttpServletRequest request) {
		ModelAndView modelAndView = new ModelAndView("/taskMgr/setTaskReceiver");
		if (StringUtils.isEmpty(taskId)) {
			return modelAndView;
		}
		ActivityInstanceModel activityInstanceModel = processInstanceService
				.getTask(taskId);
		if (activityInstanceModel == null) {
			return modelAndView;
		}
		modelAndView.addObject("activityInstanceModel", activityInstanceModel);
		return modelAndView;
	}

	/**
	 * 重新分配人员
	 * 
	 * @param taskId
	 * @param receivers
	 * @param request
	 * @return
	 */
	@RequestMapping(value = "/againSetTaskReceiver",method=RequestMethod.POST)
	@ResponseBody
	public String againSetTaskReceiver(String taskId, String receivers,
			HttpServletRequest request) {
		ActivityInstanceModel actInst = processInstanceService.getTask(taskId);
		if (actInst == null) {
			return this.ACTION_ERROR;
		}
		ProcessInputModel processInputModel = (ProcessInputModel) processInstanceService
				.getTaskVariables(actInst.getActInstId()).get(
						WorkFlowContants.WF_PROCESS_INPUT_VARIABLE_KEY);
		processInputModel.setWf_receiver(receivers);
		processInputModel.setWf_receivers(null);
		if(!StringUtils.isEmpty(actInst.getSendUserId())){
			processInputModel.setWf_sender(actInst.getSender());
			processInputModel.setWf_sendUserId(actInst.getSendUserId());
			processInputModel.setWf_sendUserOrgId(actInst.getSenderOrgId());
		}else{
			processInputModel.setWf_sender(actInst.getReceiver());
			processInputModel.setWf_sendUserId(actInst.getReceiverUserId());
			processInputModel.setWf_sendUserOrgId(actInst.getReceiverOrgId());
		}
		processInputModel
				.setWf_actionType(WorkFlowContants.ACTION_TYPE_RECEIVER_TRANSFER);
		processInputModel.setWf_curActInstId(actInst.getActInstId());
		processInputModel.setWf_curActDefId(actInst.getActivityDefinition()
				.getActDefId());
		processInputModel.setWf_curActDefName(actInst.getActivityDefinition()
				.getActDefName());
		processInputModel.setWf_procDefId(actInst.getProcDefId());
		processInputModel.setWf_procTitle(actInst.getProcTitle());
		processInputModel.setWf_procInstId(actInst.getProcInstId());
		Map<String, Object> resultMap = processOperateFacade
				.nextExecute(processInputModel);

		MyContants.saveUserOperate(request, "taskId", true, "重新分配人员成功",
				MyContants.LOGIN_SESSION_USER, MyContants.APPLICATION);
		if("ERROR".equals(resultMap.get("executeStatus"))){
			return (String) resultMap.get("executeErrorMsg");
		}
		return this.ACTION_SUCCESS;
	}

	/**
	 * 待办迁移界面
	 * 
	 * @param processInstanceId
	 * @param assignee
	 * @param assigneeName
	 * @param transferUserId
	 * @param transferUserName
	 * @param procTitle
	 * @param request
	 * @return
	 */
	@RequestMapping(value = "/taskTransferList")
	public ModelAndView taskTransferList(String processInstanceId,String dataType,
			String assignee, String assigneeName, String transferUserId,
			String transferUserName, String procTitle,
			HttpServletRequest request) {
		String appId = BaseUser.getInstance().getLoginUserAppId(request);
		
		PageRequest query = this
				.bindPageRequest(request, new PageRequest(), "");
		Page<ActivityInstanceModel> page = null;
		/*
		 * //查询组织ID不匹配数据 if(StringUtils.isNotEmpty(dataType)&&"1".equals(dataType)){
		 * query.setPageSize(10000); List<ActivityInstanceModel>
		 * actModels1=processUserOrgMatchService.findActivityInstanceByUserOrgNotMathch(
		 * appId); page=new Page<ActivityInstanceModel>(query,actModels1.size());
		 * page.setResult(actModels1); }else
		 * if(StringUtils.isNotEmpty(dataType)&&"2".equals(dataType)){//查询用户不匹配数据
		 * query.setPageSize(10000); List<ActivityInstanceModel>
		 * actModels2=processUserOrgMatchService.findActivityInstanceByUserNotMathch(
		 * appId); page=new Page<ActivityInstanceModel>(query,actModels2.size());
		 * page.setResult(actModels2); }else{
		 *///正常数据
			TaskQuery taskQuery = processInstanceService.getTaskService()
					.createTaskQuery();
			if ("true".equalsIgnoreCase(MyContants.IS_OPEN_TENANT)
					&& !StringUtils.isEmpty(appId)) {
				taskQuery.taskTenantId(appId);
			}
			if (!StringUtils.isEmpty(processInstanceId)) {
				taskQuery.procTitle(processInstanceId);
			}
			if (!StringUtils.isEmpty(assignee)) {
				taskQuery.taskAssignee(assignee);
			}
			if (!StringUtils.isEmpty(procTitle)) {
				taskQuery.processInstanceId(procTitle);
			}
			page=new Page<ActivityInstanceModel>(query, (int) taskQuery.count());
			List<Task> tasks = taskQuery.orderByTaskCreateTime().desc()
					.listPage(page.getFirstResult(), page.getPageSize());
			List<ActivityInstanceModel> actModels0=new ArrayList<ActivityInstanceModel>();
			for (Task task : tasks) {
				try {
					actModels0.add(ActivityInstanceModel.buildAndActDef((TaskEntity)task, new ActivityDefinitionModel()));
					
					
				} catch (Exception e) {
					e.printStackTrace();
				}
			}
			page.setResult(actModels0);
		//}
		ModelAndView modelAndView = new ModelAndView(
				"/taskMgr/taskTransferList");
		modelAndView.addAllObjects(toModelMap(page, null));
		modelAndView.addObject("processInstanceId", processInstanceId);
		modelAndView.addObject("assignee", assignee);
		modelAndView.addObject("dataType", dataType);
		modelAndView.addObject("assigneeName", assigneeName);
		modelAndView.addObject("transferUserId", transferUserId);
		modelAndView.addObject("transferUserName", transferUserName);
		modelAndView.addObject("procTitle", procTitle);
		return modelAndView;
	}
	
	

	/**
	 * 待办迁移
	 * 
	 * @param taskIds
	 * @param assignee
	 * @param transferUserId
	 * @param transferDatatype
	 * @param request
	 * @return
	 */
	@RequestMapping(value = "/taskTransfer",method=RequestMethod.POST)
	@ResponseBody
	public String taskTransfer(String[] taskIds, String assignee,
			String transferUserId, String transferDatatype,
			HttpServletRequest request) {
		if (((taskIds == null || taskIds.length == 0) && "0"
				.equals(transferDatatype))
				|| StringUtils.isEmpty(transferUserId)) {
			return this.ACTION_ERROR;
		}
		boolean result = processInstanceService.taskTransfer(taskIds, assignee,
				transferUserId, transferDatatype);
		MyContants.saveUserOperate(request,
				"taskIds;assignee;transferUserId;transferDatatype", result,
				result ? "待办迁移成功" : "待办迁移失败", MyContants.LOGIN_SESSION_USER,
				MyContants.APPLICATION);
		return result ? this.ACTION_SUCCESS : this.ACTION_ERROR;
	}
	
	

	/**
	 * 重新分配人员界面
	 * 
	 * @param taskId
	 * @param request
	 * @return
	 */
	@RequestMapping(value = "/addMultiInstanceView")
	public ModelAndView addMultiInstanceView(String taskId,
			HttpServletRequest request) {
		ModelAndView modelAndView = new ModelAndView("/taskMgr/addMultiInstance");
		if (StringUtils.isEmpty(taskId)) {
			return modelAndView;
		}
		ActivityInstanceModel activityInstanceModel = processInstanceService
				.getTask(taskId);
		if (activityInstanceModel == null) {
			return modelAndView;
		}
		modelAndView.addObject("activityInstanceModel", activityInstanceModel);
		return modelAndView;
	}

	/**
	 * 重新分配人员
	 * 
	 * @param taskId
	 * @param receivers
	 * @param request
	 * @return
	 */
	@RequestMapping(value = "/addMultiInstance",method=RequestMethod.POST)
	@ResponseBody
	public String addMultiInstance(String taskId, String receivers,
			HttpServletRequest request) {
		ActivityInstanceModel actInst = processInstanceService.getTask(taskId);
		if (actInst == null) {
			return this.ACTION_ERROR;
		}
		ProcessInputModel processInputModel = (ProcessInputModel) processInstanceService
				.getTaskVariables(actInst.getActInstId()).get(
						WorkFlowContants.WF_PROCESS_INPUT_VARIABLE_KEY);
		processInputModel.setWf_receiver(receivers);
		processInputModel.setWf_receivers(null);
		processInputModel.setWf_curActInstId(actInst.getPrevActInstId());
		processInputModel.setWf_curActDefId(actInst.getPrevActDefId());
		processInputModel.setWf_sendUserId(actInst.getSendUserId());
		processInputModel.setWf_sendUserOrgId(actInst.getSenderOrgId());
		processInputModel.setWf_curActDefName(actInst.getPrevActDefName());
		processInputModel.setWf_procDefId(actInst.getProcDefId());
		processInputModel.setWf_procTitle(actInst.getProcTitle());
		processInputModel.setWf_procInstId(actInst.getProcInstId());
		processInputModel
				.setWf_actionType(WorkFlowContants.ACTION_TYPE_ADD_MULTIINSTANCE_ACTIVITY);
		Map<String, Object> resultMap = processOperateFacade
				.nextExecute(processInputModel);
		if("ERROR".equals(resultMap.get("executeStatus"))){
			return (String) resultMap.get("executeErrorMsg");
		}
		return this.ACTION_SUCCESS;
	}
	@RequestMapping(value = "/deleteMultiInstance",method=RequestMethod.POST)
	@ResponseBody
	public Map<String, Object> deleteMultiInstance(String taskId, String receivers,
			HttpServletRequest request){
		ActivityInstanceModel actInst = processInstanceService.getTask(taskId);
		if (actInst == null) {
			return null;
		}
		ProcessInputModel processInputModel = (ProcessInputModel) processInstanceService
				.getTaskVariables(actInst.getActInstId()).get(
						WorkFlowContants.WF_PROCESS_INPUT_VARIABLE_KEY);
		processInputModel.setWf_receiver(actInst.getReceiver());
		processInputModel.setWf_receivers(null);
		processInputModel.setWf_curActInstId(actInst.getActInstId());
		processInputModel.setWf_curActDefId(actInst.getActDefId());
		processInputModel.setWf_curActDefName(actInst.getActDefName());
		processInputModel.setWf_procDefId(actInst.getProcDefId());
		processInputModel.setWf_procTitle(actInst.getProcTitle());
		processInputModel.setWf_procInstId(actInst.getProcInstId());
		processInputModel
				.setWf_actionType(WorkFlowContants.ACTION_TYPE_DELETE_MULTIINSTANCE_ACTIVITY);
		Map<String, Object> resultMap = processOperateFacade
				.nextExecute(processInputModel);
		return resultMap;
	}
}
