package com.blueland.bpm.manage.countAnalysis.service;

import com.blueland.bpm.engine.util.BaseSpringJdbcDao;
import com.blueland.bpm.manage.countAnalysis.dao.ProcessMonitorDao;
import groovy.util.logging.Slf4j;
import net.sf.json.JSONArray;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

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

/**
 * @作者     dsl
 * @创建时间  2020年2月5日
 * @说明   流程监控
 */
@Slf4j
@Service
public class ProcessMonitorService{
	@Autowired
	private ProcessMonitorDao processMonitorDao;
	/**
	 * 流程分析详情
	 * 待办最多流程、超时处理最多流程、创建量最高流程、平均审批耗时最长流程
	 * @return
	 */
	public List<Map<String, Object>> analysisDetail() {
		List<Map<String,Object>> list = new ArrayList<Map<String,Object>>();
		//待办最多流程
		List<Map<String,Object>> daiBanList = processMonitorDao.getDoProcesss(null);
		list.add(this.appendData("daiBanTotal",daiBanList,"APP_ID"));
		//超时最多的流程
		List<Map<String,Object>> overTimeList = processMonitorDao.getOutTimeProcess(null);
		list.add(this.appendOverData("overTimeTotal",overTimeList,"APP_ID"));
		//创建最多的流程
		List<Map<String,Object>> createProcessList = processMonitorDao.getCreateProcess();
		list.add(this.appendCreateData("createProcessTotal",createProcessList));
		//耗时最长的流程
		List<Map<String,Object>> maxUserTimeList = processMonitorDao.getUseTimeMaxProcess(null);
		list.add(this.appendData("avgUserTimeTotal",maxUserTimeList,"APP_ID"));
		
		Map<String,Object> obj = new HashMap<String, Object>();
		obj.put("id", "params");
		obj.put("daiBan", daiBanList.size()>0?daiBanList.get(0).get("NAME"):0);
		obj.put("avgUserTimeprocess", maxUserTimeList.size()>0?maxUserTimeList.get(0).get("NAME"):0);
		obj.put("overTimeprocess", overTimeList.size()>0? overTimeList.get(0).get("PROC_DEF_NAME"):0);
		obj.put("createMostprocess", createProcessList.size()>0? createProcessList.get(0).get("PROC_DEF_NAME"):0);
		list.add(obj);
		return list;
	}
	/**
	 * 组装创建最多的流程
	 * @param createProcessList
	 * @return
	 */
	private Map<String, Object> appendCreateData(String id, List<Map<String, Object>> createProcessList) {
		Map<String,Object> result = new HashMap<String, Object>();
		ArrayList list =new ArrayList();
		//总计
		List<Map<String,Object>> totalDatas = new ArrayList<Map<String,Object>>();
		//运行中
		List<Map<String,Object>> runDatas = new ArrayList<Map<String,Object>>();
		//已完成
		List<Map<String,Object>> finishDatas = new ArrayList<Map<String,Object>>();
		//作废
		List<Map<String,Object>> cancleDatas = new ArrayList<Map<String,Object>>();
		result.put("id", id);
		for (Map<String,Object> obj : createProcessList) {
			Map<String,Object> runData = new HashMap<String, Object>();
			Map<String,Object> finishData = new HashMap<String, Object>();
			Map<String,Object> cancleData = new HashMap<String, Object>();
			Integer cancle =Integer.parseInt(obj.get("CANCLE") != null?obj.get("CANCLE").toString():"0");
			Integer un_deal =Integer.parseInt(obj.get("UN_DEAL") != null?obj.get("UN_DEAL").toString():"0");
			Integer deal =Integer.parseInt(obj.get("DEAL") != null?obj.get("DEAL").toString():"0");
			String appId = obj.get("APP_ID").toString();
			cancleData.put("id", obj.get("PROC_DEF_NAME").toString());
			cancleData.put("y",cancle);
			cancleData.put("appId",appId);
			cancleData.put("title","已完成:"+deal+"（个）"
					+"<br>运行中:"+un_deal+"（个）"
					+"<br>已作废:"+cancle+"（个）");
			cancleDatas.add(cancleData);
			
			runData.put("id", obj.get("PROC_DEF_NAME").toString());
			runData.put("y",un_deal);
			runData.put("appId",appId);
			runData.put("title","已完成:"+deal+"（个）"
					+"<br>运行中:"+un_deal+"（个）"
					+"<br>已作废:"+cancle+"（个）");
			runDatas.add(runData);
			
			finishData.put("id", obj.get("PROC_DEF_NAME").toString());
			finishData.put("y",deal);
			finishData.put("appId",appId);
			finishData.put("title","已完成:"+deal+"（个）"
					+"<br>运行中:"+un_deal+"（个）"
					+"<br>已作废:"+cancle+"（个）");
			finishDatas.add(finishData);
			list.add(obj.get("PROC_DEF_NAME").toString());
		}
		result.put("datas", "["
				+ "{name:"+"'已作废',"+"data:"+JSONArray.fromObject(cancleDatas)+"},"
				+ "{name:"+"'运行中',"+"data:"+JSONArray.fromObject(runDatas)+"},"
				+ "{name:"+"'已完成',"+"data:"+JSONArray.fromObject(finishDatas)+"}]");
		result.put("list", list);
		return result;
	}
	/**
	 * 组装超时最多的流程数据
	 * @param overTimeList
	 * @param key 
	 * @return
	 */
	private Map<String, Object> appendOverData(String id, List<Map<String, Object>> overTimeList, String key) {
		Map<String,Object> result = new HashMap<String, Object>();
		ArrayList list =new ArrayList();
		List<Map<String,Object>> runDatas = new ArrayList<Map<String,Object>>();
		List<Map<String,Object>> finishDatas = new ArrayList<Map<String,Object>>();
		result.put("id", id);
		for (Map<String,Object> obj : overTimeList) {
			Map<String,Object> runData = new HashMap<String, Object>();
			Map<String,Object> finishData = new HashMap<String, Object>();
			Double finish = Double.parseDouble(obj.get("FINISH_OVER_TIME") != null?obj.get("FINISH_OVER_TIME").toString():"0");
			Double run = Double.parseDouble(obj.get("RUN_OVER_TIME") != null?obj.get("RUN_OVER_TIME").toString():"0");
			runData.put("id", obj.get(key).toString());
			runData.put("y", run);
			runData.put("appId", obj.get("APP_ID").toString());
			runData.put("title", "<br>已完成:"+finish+"（小时）<br>运行中:"+run+"（小时）");
			runDatas.add(runData);
			finishData.put("id", obj.get(key).toString());
			finishData.put("y",finish);
			finishData.put("appId", obj.get("APP_ID").toString());
			finishData.put("title", "<br>已完成:"+finish+"（小时）<br>运行中:"+run+"（小时）");
			finishDatas.add(finishData);
			list.add(obj.get("PROC_DEF_NAME").toString());
		}
		result.put("datas", "[{name:"+"'运行中',"+"data:"+JSONArray.fromObject(runDatas)+"},{name:"+"'已完成',"+"data:"+JSONArray.fromObject(finishDatas)+"}]");
		result.put("list", list);
		return result;
	}
	/**
	 * 组装待办流程最多的数据
	 * @param daiBanList
	 * @param key 
	 * @return
	 */
	private Map<String, Object> appendData(String id, List<Map<String, Object>> daiBanList, String key) {
		Map<String,Object> result = new HashMap<String, Object>();
		ArrayList list =new ArrayList();
		List<Map<String,Object>> datas = new ArrayList<Map<String,Object>>();
		result.put("id", id);
		for (Map<String,Object> obj : daiBanList) {
			Map<String,Object> data = new HashMap<String, Object>();
			data.put("name", obj.get("NAME").toString());
			data.put("y", Double.parseDouble(obj.get("COUNT").toString()));
			data.put("id", obj.get(key).toString());
			data.put("appId", obj.get("APP_ID").toString());
			datas.add(data);
			list.add(obj.get("NAME").toString());
		}
		result.put("datas", "[{name:"+"'',"+"data:"+JSONArray.fromObject(datas)+"}]");
		result.put("list", list);
		return result;
	}
	/**
	 *  * 节点分析详情
	 * 节点平均耗时、待办流程最多的节点
	 * @return
	 */
	public List<Map<String, Object>> actAnalysisDetail() {
		List<Map<String,Object>> list = new ArrayList<Map<String,Object>>();
		//节点平均耗时
		List<Map<String,Object>> actUserTimeList = processMonitorDao.getActAvgUseTime(null);
		list.add(this.appendData("actAvgUserTimeTotal",actUserTimeList,"APP_ID"));
		//待办流程最多的节点
		List<Map<String,Object>> doTaskActList = processMonitorDao.getDoTaskMaxAct(null);
		list.add(this.appendData("actUserTimeTotal",doTaskActList,"APP_ID"));
		Map<String,Object> obj = new HashMap<String, Object>();
		obj.put("id", "params");
		obj.put("actUserTime", actUserTimeList.size()>0?actUserTimeList.get(0).get("NAME"):0);
		obj.put("doTaskAct", doTaskActList.size()>0?doTaskActList.get(0).get("NAME"):0);
		list.add(obj);
		return list;
	}
	/**
	 * 人员分析详情
	 * 待处理流程最多的员工
	 * @return
	 */
	public List<Map<String, Object>> staffAnalysisDetail() {
		List<Map<String,Object>> list = new ArrayList<Map<String,Object>>();
		//节点平均耗时
		List<Map<String,Object>> staffTopList = processMonitorDao.getTopUserTask(null);
		list.add(this.appendData("staffTopTotal",staffTopList,"APP_ID"));
		Map<String,Object> obj = new HashMap<String, Object>();
		obj.put("id", "params");
		obj.put("staffTop", staffTopList.size()>0?staffTopList.get(0).get("NAME"):0);
		list.add(obj);
		return list;
	}
	public List<Map<String, Object>> appProcessDetail(String appId) {
		List<Map<String,Object>> list = new ArrayList<Map<String,Object>>();
		//待办流程最多的节点
		Map<String,Object> params = new HashMap<String, Object>();
		params.put("appId", appId);
		List<Map<String,Object>> doTaskActList = processMonitorDao.getDoProcesss(params);
		list.add(this.appendData("doTaskActTotal",doTaskActList,"NAME"));
		Map<String,Object> totalData = processMonitorDao.getDoTotalProcesss();
		Map<String,Object> obj = new HashMap<String, Object>();
		obj.put("id", "params");
		obj.put("doTaskAct", doTaskActList.size()>0?doTaskActList.get(0).get("NAME"):0);
		obj.put("processTotal", totalData.get("COUNT"));
		obj.put("staffTotal", totalData.get("STAFFCOUNT"));
		//this.appendTotal(doTaskActList,obj);
		list.add(obj);
		return list;
	}
	/**
	 * 组装流程总数和人员总数数据
	 * @param doTaskActList
	 * @param obj
	 * @return
	 */
	private Map<String,Object> appendTotal(List<Map<String, Object>> doTaskActList, Map<String, Object> obj) {
		int processTotal = 0;
		int staffTotal = 0;
		for (Map<String,Object> task : doTaskActList) {
			processTotal = processTotal+Integer.parseInt(task.get("COUNT").toString());
			staffTotal = staffTotal+Integer.parseInt(task.get("STAFFCOUNT").toString());
		}
		obj.put("processTotal", processTotal);
		obj.put("staffTotal", staffTotal);
		return obj;
	}
	/**
	 * 平均耗时最长的流程统计详情
	 * @param appId
	 * @return
	 */
	public List<Map<String, Object>> avgUserTimeDetail(String appId) {
		List<Map<String,Object>> list = new ArrayList<Map<String,Object>>();
		Map<String,Object> params = new HashMap<String, Object>();
		params.put("appId", appId);
		//节点平均耗时
		List<Map<String,Object>> actUserTimeList = processMonitorDao.getUseTimeMaxProcess(params);
		list.add(this.appendData("actAvgUserTimeTotal",actUserTimeList,"NAME"));
		Map<String,Object> obj = new HashMap<String, Object>();
		obj.put("id", "params");
		obj.put("actUserTime", actUserTimeList.size()>0?actUserTimeList.get(0).get("NAME"):0);
		Map<String,Object> actUserTimeTotal = processMonitorDao.getUseTimeMaxProcessTotal();
		obj.put("processTotal", actUserTimeTotal.get("TOTAL"));
		obj.put("modelTotal", actUserTimeTotal.get("MODELTOTAL"));
		//this.appendUserTimeTotal(actUserTimeList,obj,"TOTAL");
		list.add(obj);
		return list;
	}
	/**
	 * 超时处理最多的流程详情
	 * @param appId
	 * @return
	 */
	public List<Map<String, Object>> overTimeProcessDetail(String appId) {
		List<Map<String,Object>> list = new ArrayList<Map<String,Object>>();
		Map<String,Object> params = new HashMap<String, Object>();
		params.put("appId", appId);
		//超时最多的流程
		List<Map<String,Object>> overTimeList = processMonitorDao.getOutTimeProcess(params);
		list.add(this.appendOverData("overTimeTotal",overTimeList,"PROC_DEF_NAME"));
		List<Map<String,Object>> overTimeTotal = processMonitorDao.getOutTimeProcessTotal();
		Map<String,Object> obj = new HashMap<String, Object>();
		obj.put("id", "params");
		obj.put("actUserTime", overTimeList.size()>0?overTimeList.get(0).get("PROC_DEF_NAME"):0);
		obj.put("processTotal", overTimeTotal.get(0).get("COUNT"));
		obj.put("modelTotal", overTimeTotal.get(1).get("COUNT"));
		//this.appendUserTimeTotal(overTimeList,obj,"TOTAL");
		list.add(obj);
		return list;
	}
	
	/**
	 * 组装平均耗时最长的数据
	 * @param actUserTimeList
	 * @param obj
	 * @param key 
	 * @return
	 */
	private Map<String,Object> appendUserTimeTotal(List<Map<String, Object>> actUserTimeList, Map<String, Object> obj, String key) {
		int processTotal = 0;
		for (Map<String,Object> task : actUserTimeList) {
			processTotal = processTotal+Integer.parseInt(task.get(key).toString());
		}
		obj.put("processTotal", processTotal);
		obj.put("modelTotal", actUserTimeList.size());
		return obj;
		
	}
	/**
	 * 节点平均耗时-下钻详情
	 * @param appId
	 * @return
	 * @throws Exception
	 */
	public List<Map<String, Object>> actAvgUserTimeDetail(String appId) {
		List<Map<String,Object>> list = new ArrayList<Map<String,Object>>();
		Map<String,Object> params = new HashMap<String, Object>();
		params.put("appId", appId);
		//节点平均耗时
		List<Map<String,Object>> actUserTimeList = processMonitorDao.getActAvgUseTime(params);
		list.add(this.appendData("actAvgUserTimeTotal",actUserTimeList,"TASK_DEF_KEY"));
		Map<String,Object> obj = new HashMap<String, Object>();
		obj.put("id", "params");
		obj.put("actUserTime", actUserTimeList.size()>0?actUserTimeList.get(0).get("NAME"):0);
		Map<String,Object> actUserTimeTotal = processMonitorDao.getActAvgUseTimeTotal();
		obj.put("processTotal", actUserTimeTotal.get("TOTAL"));
		obj.put("modelTotal", actUserTimeTotal.get("STAFFCOUNT"));
		//this.appendUserTimeTotal(actUserTimeList,obj,"TOTAL");
		list.add(obj);
		return list;
	}
	/**
	 * 人员分析-下钻详情
	 * @param appId
	 * @return
	 */
	public List<Map<String, Object>> staffTopDetail(String appId) {
		List<Map<String,Object>> list = new ArrayList<Map<String,Object>>();
		//节点平均耗时
		Map<String,Object> params = new HashMap<String, Object>();
		params.put("appId", appId);
		List<Map<String,Object>> staffTopList = processMonitorDao.getTopUserTask(params);
		list.add(this.appendData("staffTopTotal",staffTopList,"APP_ID"));
		Map<String,Object> totalData = processMonitorDao.getDoTotalProcesss();
		Map<String,Object> obj = new HashMap<String, Object>();
		obj.put("id", "params");
		obj.put("staffTop", staffTopList.size()>0?staffTopList.get(0).get("NAME"):0);
		obj.put("processTotal", totalData.get("COUNT"));
		obj.put("staffTotal", totalData.get("STAFFCOUNT"));
		//this.appendUserTimeTotal(staffTopList,obj,"COUNT");
		list.add(obj);
		return list;
	}
	/**
	 * 流程创建数量排名详情
	 * @param appId
	 * @return
	 */
	public List<Map<String, Object>> createMaxProcessDetail(String appId) {
		List<Map<String,Object>> list = new ArrayList<Map<String,Object>>();
		//创建最多的流程
	    List<Map<String,Object>> createProcessList = processMonitorDao.getCreateProcess();
	    list.add(this.appendCreateData("createProcessTotal",createProcessList));
	    Map<String,Object> createMaxTotal = processMonitorDao.getCreateProcessTotal();
	    Map<String,Object> obj = new HashMap<String, Object>();
		obj.put("id", "params");
		obj.put("total", createMaxTotal.get("CREATECOUNT")!=null?createMaxTotal.get("CREATECOUNT"):0);
		obj.put("un_deal", createMaxTotal.get("UN_DEAL")!=null?createMaxTotal.get("UN_DEAL"):0);
		obj.put("deal", createMaxTotal.get("DEAL")!=null?createMaxTotal.get("DEAL"):0);
		obj.put("cancle", createMaxTotal.get("CANCLE")!=null?createMaxTotal.get("CANCLE"):0);
		list.add(obj);
	    return list;
	}
	/**
	 * 节点分析-待审流程最多的节点下钻详情
	 * @param appId
	 * @return
	 */
	public List<Map<String, Object>> actDoProcessDetail(String appId) {
		List<Map<String,Object>> list = new ArrayList<Map<String,Object>>();
		//待办流程最多的节点
		List<Map<String,Object>> doTaskActList = processMonitorDao.getDoTaskMaxAct(null);
		list.add(this.appendData("doTaskActTotal",doTaskActList,"TASK_DEF_KEY"));
		Map<String,Object> totalData = processMonitorDao.getDoTotalProcesss();
		Map<String,Object> obj = new HashMap<String, Object>();
		obj.put("id", "params");
		obj.put("doTaskAct", doTaskActList.size()>0?doTaskActList.get(0).get("NAME"):0);
		obj.put("processTotal", totalData.get("COUNT"));
		obj.put("staffTotal", totalData.get("STAFFCOUNT"));
		list.add(obj);
		return list;
	}
	
}
