package com.engine.kq.wfset.attendance.manager;

import com.engine.kq.cmd.hrmAttProcSet.SaveStateProcCheckRuleCmd;
import com.google.common.collect.Maps;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

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

import org.apache.commons.beanutils.BeanUtils;

import weaver.common.StringUtil;
import com.engine.kq.wfset.attendance.framework.BaseManager;
import com.engine.kq.wfset.attendance.dao.HrmAttFlowVersionDao;
import com.engine.kq.wfset.attendance.domain.HrmAttFlowVersion;
import com.engine.kq.wfset.attendance.domain.HrmAttProcAction;
import com.engine.kq.wfset.attendance.domain.HrmAttProcRelation;
import com.engine.kq.wfset.attendance.domain.HrmAttProcSet;
import weaver.conn.RecordSet;
import weaver.general.Util;
import weaver.hrm.User;
import weaver.hrm.pm.domain.HrmStateProcAction;
import weaver.hrm.pm.domain.HrmStateProcRelation;
import weaver.hrm.pm.domain.HrmStateProcSet;
import weaver.hrm.pm.manager.HrmStateProcActionManager;
import weaver.hrm.pm.manager.HrmStateProcRelationManager;
import weaver.hrm.pm.manager.HrmStateProcSetManager;

/**
 * HrmAttFlowVersionManager
 * <p>Generated from 长东设计1.0.9 http://www.mfstyle.cn</p> 
 * 
 * @author wcd
 * @version 1.0 2016-05-31
 */
public class HrmAttFlowVersionManager extends BaseManager<HrmAttFlowVersion> {

	private HrmAttFlowVersionDao dao = null;

	public HrmAttFlowVersionManager() {
		this(null, null);
	}

	public HrmAttFlowVersionManager(HttpServletRequest request, HttpServletResponse response) {
		super(request, response);
		this.setDao(dao = new HrmAttFlowVersionDao());
	}

	public Long save(HrmAttFlowVersion bean) {
		return save(bean, false);
	}

	public Long save(HrmAttFlowVersion bean, boolean isNew) {
		return -1L;
	}

	public void save(List<HrmAttFlowVersion> list) {
		dao.insert(list);
	}

	public int count(String params) {
		return dao.count(this.getMapParam(params));
	}

	public void delete(Map<String, Comparable> map) {
		dao.delete(map);
	}
	
	/**
	 * 流程存为新版时，复制考勤流程设置、人事状态变更设置
	 * @param oldWfId
	 * @param newWfID
	 */
	public void copySet(final String oldWfId, final String newWfId) {
		new Thread(new Runnable() {
			public void run() {
				try {
					HrmAttFlowVersion bean = new HrmAttFlowVersion(oldWfId, newWfId);
					if(!bean.isError()) {
						copyAttProcSet(bean.toAttProc());
						copyStateProcSet(bean.toStateProc());
					}
				} catch (Exception e) {
					writeLog(e);
				}
			}
		}).start();
	}
	
	/**
	 * 复制考勤流程设置
	 * @param bean
	 */
	private void copyAttProcSet(HrmAttFlowVersion bean) {
		HrmAttProcSet setBean = null, newSetbean = new HrmAttProcSet();
		com.engine.kq.wfset.attendance.manager.HrmAttProcSetManager setManager = new HrmAttProcSetManager();
		if(!dao.allowedToCopy(bean) || (setBean = setManager.get("[map]field001:"+bean.getField001())) == null) return;
		
		try {BeanUtils.copyProperties(newSetbean, setBean);} catch (Exception e) {}
		newSetbean.setId(0L);
		newSetbean.setField001(StringUtil.parseToInt(bean.getField002()));
		newSetbean.setMfid(StringUtil.getUUID());
		Long newSetId = setManager.save(newSetbean);
    newSetbean.setId(newSetId);
		
		HrmAttProcRelationManager rManager = new HrmAttProcRelationManager();
		List<HrmAttProcRelation> relationList = rManager.find("[map]field001:"+setBean.getId());
		for(HrmAttProcRelation rBean : relationList) rBean.setField001(newSetId.intValue());
		rManager.save(relationList);
		
		com.engine.kq.wfset.attendance.manager.HrmAttProcActionManager aManager = new HrmAttProcActionManager();
		List<HrmAttProcAction> actionList = aManager.find("[map]field001:"+setBean.getId());
		for(HrmAttProcAction aBean : actionList) {
			aBean.setField001(newSetId);
      int old_nodeid = Util.getIntValue(aBean.getField006());
      String new_nodeid = ""+getNodeidByWfidAndOldnodeid(Util.getIntValue(bean.getField002()), old_nodeid);
			aBean.setMfid(StringUtil.getUUID());
      aBean.setField006(new_nodeid);
		}
		aManager.save(actionList);

		saveCheckRule(setBean,newSetbean);
	}

  /**
   * 考勤流程设置里的校验规则也需要存为新版本
   * @param setBean
   * @param newSetbean
   */
  public void saveCheckRule(HrmAttProcSet setBean,
      HrmAttProcSet newSetbean) {
    RecordSet rs = new RecordSet();
    RecordSet rs1 = new RecordSet();
    RecordSet rs2 = new RecordSet();
    RecordSet rs3 = new RecordSet();
    long old_att_id = setBean.getId();
    long new_att_id = newSetbean.getId();
    int field006 = newSetbean.getField006();
    String sql = "select * from kq_att_checkrule_set where attid = ? ";
    rs.executeQuery(sql, old_att_id);
    while (rs.next()){
      Map<String, Object> params = Maps.newHashMap();
      String rule_type_uuid = rs.getString("rule_type_uuid");
      String ruleid = rs.getString("ruleid");
      params.put("attid", new_att_id);
      params.put("kqtype", field006);
      params.put("rule_type_uuid", rule_type_uuid);
      String sql1 = "select * from kq_att_checkrule_type where uuid = ? and att_type=? ";
      rs1.executeQuery(sql1,rule_type_uuid,field006);
      while (rs1.next()){
        String rule_table = rs1.getString("rule_table");
        String sql2 = "select * from "+rule_table+" where id=? ";
        rs2.executeQuery(sql2, ruleid);
        while (rs2.next()){
          String fieldSql = "select * from kq_att_checkrule_fields where rule_type_uuid = ? order by fieldorder ";
          rs3.executeQuery(fieldSql,rule_type_uuid);
          while (rs3.next()){
            String fieldname = rs3.getString("fieldname");
            String field_value = rs2.getString(fieldname);
            params.put(fieldname, field_value);
          }
        }
      }
      SaveStateProcCheckRuleCmd saveStateProcCheckRuleCmd = new SaveStateProcCheckRuleCmd(params, new User(1));
      saveStateProcCheckRuleCmd.execute(null);
    }

  }

  /**
   * 流程存为新版后，根据旧版本的节点id，获取当前路径中该节点对应的节点id
   * @param newWfId
   * @param nodeid_old
   * @return
   */
  public int getNodeidByWfidAndOldnodeid(int newWfId,int nodeid_old){
    int newNodeid = -1;
    RecordSet rs = new RecordSet();
    List<String> childrenNodeList = getChildrenNodeListByNodeID(nodeid_old+"");
    int childrenNodeList_len = childrenNodeList.size();
    if(childrenNodeList_len == 0){
      return newNodeid;
    }

    String sql = "select max(nodeid) maxnodeid from workflow_flownode where nodeid in ( ";
    for(int i=0;i<childrenNodeList_len;i++){
      if(i>0){
        sql += ",";
      }
      sql += "?";
    }
    sql += " ) and workflowid = ?";
    childrenNodeList.add(String.valueOf(newWfId));

    rs.executeQuery(sql, childrenNodeList);
    if(rs.next()){
      newNodeid = rs.getInt("maxnodeid");
    }
    return newNodeid;
  }
  /**
   * 根据节点id，获取与之相关的所有子节点
   * @param parentnodeid
   * @return
   */
  public static List<String> getChildrenNodeListByNodeID(String parentnodeid) {

    List<String> nodes = new ArrayList<String>();

    if (parentnodeid == null || "".equals(parentnodeid.trim())) {
      return nodes;
    }

    RecordSet rs = new RecordSet();
    String sql = "select nodeid, parentnodeid from workflow_versionNodeRelation where parentnodeid=" + parentnodeid;
    rs.execute(sql);
    while (rs.next()) {
      String nodeid = rs.getString("nodeid");
      nodes.add(nodeid);
      nodes.addAll(getChildrenNodeListByNodeID(nodeid));
    }
    return nodes;
  }

	/**
	 * 复制人事状态变更设置
	 * @param bean
	 */
	private void copyStateProcSet(HrmAttFlowVersion bean) {
		HrmStateProcSet setBean = null, newSetbean = new HrmStateProcSet();
		HrmStateProcSetManager setManager = new HrmStateProcSetManager();
		if(!dao.allowedToCopy(bean) || (setBean = setManager.get("[map]field001:"+bean.getField001())) == null) return;
		
		try {BeanUtils.copyProperties(newSetbean, setBean);} catch (Exception e) {}
		newSetbean.setId(0L);
		newSetbean.setMfid(StringUtil.getUUID());
		newSetbean.setField001(StringUtil.parseToInt(bean.getField002()));
		Long newSetId = setManager.save(newSetbean);
		
		HrmStateProcRelationManager rManager = new HrmStateProcRelationManager();
		List<HrmStateProcRelation> relationList = rManager.find("[map]field001:"+setBean.getId());
		for(HrmStateProcRelation rBean : relationList) rBean.setField001(newSetId.intValue());
		rManager.save(relationList);
		
		HrmStateProcActionManager aManager = new HrmStateProcActionManager();
		List<HrmStateProcAction> actionList = aManager.find("[map]field001:"+setBean.getId());
		for(HrmStateProcAction aBean : actionList) {
			aBean.setField001(newSetId);
			aBean.setMfid(StringUtil.getUUID());
		}
		aManager.save(actionList);
	}

}
